package com.qianwen.core.sequence.sequence.impl; import cn.hutool.core.date.DatePattern; import cn.hutool.core.date.DateUtil; import java.util.Date; import java.util.Map; import java.util.concurrent.ConcurrentHashMap; import java.util.concurrent.locks.Lock; import java.util.concurrent.locks.ReentrantLock; import com.qianwen.core.sequence.exception.SeqException; import com.qianwen.core.sequence.range.BizName; import com.qianwen.core.sequence.range.SeqRange; import com.qianwen.core.sequence.range.SeqRangeMgr; import com.qianwen.core.sequence.sequence.RangeSequence; public class DefaultRangeSequence implements RangeSequence { private final Lock lock = new ReentrantLock(); private SeqRangeMgr seqRangeMgr; private volatile SeqRange currentRange; private static Map seqRangeMap = new ConcurrentHashMap(8); private BizName bizName; private Integer step; private long startStep; @Override // com.qianwen.core.sequence.sequence.RangeSequence public void setSeqRangeMgr(SeqRangeMgr seqRangeMgr) { this.seqRangeMgr = seqRangeMgr; } @Override // com.qianwen.core.sequence.sequence.RangeSequence public void setName(BizName name) { this.bizName = name; } @Override // com.qianwen.core.sequence.sequence.RangeSequence public void setStep(Integer step) { this.step = step; } @Override // com.qianwen.core.sequence.sequence.RangeSequence public void setStartStep(long startStep) { this.startStep = startStep; } @Override // com.qianwen.core.sequence.sequence.Sequence public long nextValue() throws SeqException { String name = this.bizName.create(); this.currentRange = seqRangeMap.get(name); if (null == this.currentRange) { this.lock.lock(); try { if (null == this.currentRange) { this.currentRange = this.seqRangeMgr.nextRange(name); seqRangeMap.put(name, this.currentRange); } } finally { } } long value = this.currentRange.getAndIncrement(); if (value == -1) { this.lock.lock(); while (true) { try { if (this.currentRange.isOver()) { this.currentRange = this.seqRangeMgr.nextRange(name); seqRangeMap.put(name, this.currentRange); } value = this.currentRange.getAndIncrement(); if (value != -1) { break; } } finally { } } } if (value < 0) { throw new SeqException("Sequence value overflow, value = " + value); } return value; } @Override // com.qianwen.core.sequence.sequence.Sequence public String nextNo() throws SeqException { return String.format("%s%05d", DateUtil.format(new Date(), DatePattern.PURE_DATE_FORMAT), Long.valueOf(nextValue())); } }