自定义编码生成
@Service
public class SequenceCodeServiceImpl implements SequenceCodeService {
public static Logger logger = LoggerFactory.getLogger(SequenceCodeService.class);
@Resource
public RedisTemplate redisTemplate;
@Resource
public CodeRulesMapper codeRulesMapper;
private static final String CODE_PUB="code:pub:";
/**
* @Description: 根据规则类型获取编码
* @param ruleType
* @return: {@link }
* @Author: lvyq
* @Date: 2022/9/21 17:04
*/
@Override
public String getCodeByRuleType(String ruleType) {
String codeRulesId =codeRulesMapper.getIdByRuleType(ruleType);
if (StringUtils.isEmpty(codeRulesId)){
throw new RuntimeException(ruleType+"编码规则不存在");
}
return getCodeByCodeRulesId(codeRulesId);
}
/**
* 根据codeRulesId获取编号
* @param codeRulesId
* @return
*/
@Override
public String getCodeByCodeRulesId(String codeRulesId) {
CodeRules codeRules = codeRulesMapper.selectById(codeRulesId);
//以codeRulesId为key进行存储
if (codeRules!=null){
return getCode(codeRules);
}else {
throw new RuntimeException("当前编码规则不存在");
}
}
/**
* 获取编码
* @param codeRules
* @return
*/
public String getCode(CodeRules codeRules) {
//前缀
String prefix = codeRules.getPrefix();
//规则类型-时间规则
String serialType=codeRules.getSerialType();
//后缀
String suffix = codeRules.getSuffix();
//自增序列位数
String serialDigitis = codeRules.getSerialDigitis();
//分隔符
String ruleSeparator = codeRules.getRuleSeparator();
if (ruleSeparator==null){ruleSeparator="";}
if (prefix==null){prefix="";}
if (suffix==null){suffix="";}
if (StringUtils.isNotEmpty(serialType)){
return getCodeNo(CODE_PUB+codeRules.getRuleType()+":"+codeRules.getId(),serialType,prefix,suffix,serialDigitis,ruleSeparator);
}else {
//无规则,无过期
return geOtherNo(CODE_PUB+codeRules.getRuleType()+":"+codeRules.getId(),prefix,suffix,serialDigitis,ruleSeparator);
}
}
/**
* 含规则
* @param key
* @param serialType
* @param prefix
* @param suffix
* @param serialDigitis
* @param ruleSeparator
* @return
*/
private String getCodeNo(String key, String serialType, String prefix, String suffix, String serialDigitis, String ruleSeparator) {
Calendar calendar = Calendar.getInstance();
//按年
if (!serialType.contains("MM") ){
//设置过期时间,这里设置为当年12月31日的23:59:59
SimpleDateFormat format = new SimpleDateFormat("yyyy");
calendar.set(Integer.valueOf(format.format(new Date())),11,31,23,59,59);
}else if (serialType.contains("dd")){
//按日,设置时间,到当日23:59:59过期
calendar.set(Calendar.HOUR_OF_DAY, 23);
calendar.set(Calendar.MINUTE, 59);
calendar.set(Calendar.SECOND, 59);
calendar.set(Calendar.MILLISECOND, 999);
}else if (serialType.contains("MM") && !serialType.contains("dd")){
//按月。设置时间,当月过期
SimpleDateFormat format = new SimpleDateFormat("MM");
calendar.set(Calendar.MONTH,Integer.valueOf(format.format(new Date())));
calendar.set(Calendar.DATE,0);//表示取当前月份的前一天
calendar.set(Calendar.HOUR_OF_DAY, 23);
calendar.set(Calendar.MINUTE, 59);
calendar.set(Calendar.SECOND, 59);
calendar.set(Calendar.MILLISECOND, 999);
}
Date expireDate = calendar.getTime();
Long seq = generate(redisTemplate, key, expireDate);
String sequence="";
//生成x位序列号,如果seq不够x位,seq前面补0,
if (StringUtils.isNotEmpty(serialDigitis)){
sequence = StringUtils.leftPad(seq.toString(), Integer.valueOf(serialDigitis), "0");
}else {
//无补位自增
sequence=seq.toString();
}
//规则日期生成
SimpleDateFormat format = new SimpleDateFormat(serialType);
//拼接业务编号
String seqNo = prefix + ruleSeparator+format.format(new Date()) +ruleSeparator+ sequence+ruleSeparator+suffix;
if (seqNo.endsWith(ruleSeparator) && StringUtils.isNotEmpty(ruleSeparator)){
seqNo=seqNo.substring(0,seqNo.length()-ruleSeparator.length());
}
if (seqNo.startsWith(ruleSeparator) && StringUtils.isNotEmpty(ruleSeparator)){
seqNo=seqNo.substring(ruleSeparator.length());
}
logger.info("KEY:{}, 序列号生成:{}, 过期时间:{}", key, seqNo, String.format("%tF %tT ", expireDate, expireDate));
return seqNo;
}
/**
* 无规则
* @param prefix
* @param suffix
* @param serialDigitis
* @param ruleSeparator
* @return
*/
public String geOtherNo(String key,String prefix,String suffix,String serialDigitis,String ruleSeparator) {
RedisAtomicLong counter = new RedisAtomicLong(key,redisTemplate.getConnectionFactory());
Long seq=counter.incrementAndGet();
String sequence="";
//生成x位序列号,如果seq不够x位,seq前面补0,
if (StringUtils.isNotEmpty(serialDigitis)){
sequence = StringUtils.leftPad(seq.toString(), Integer.valueOf(serialDigitis), "0");
}else {
//无补位自增
sequence=seq.toString();
}
//拼接业务编号 前缀+分割符+序号+分割+后缀
String seqNo=prefix+ruleSeparator+sequence+ruleSeparator+suffix;
if (seqNo.endsWith(ruleSeparator) && StringUtils.isNotEmpty(ruleSeparator)){
seqNo=seqNo.substring(0,seqNo.length()-ruleSeparator.length());
}
if (seqNo.startsWith(ruleSeparator) && StringUtils.isNotEmpty(ruleSeparator)){
seqNo=seqNo.substring(ruleSeparator.length());
}
logger.info("KEY:{}, 序列号生成:{}", key, seqNo);
return seqNo;
}
/**
* @param key
* @param expireTime <i>过期时间</i>
* @return
*/
public static long generate(RedisTemplate<?,?> redisTemplate,String key,Date expireTime) {
RedisAtomicLong counter = new RedisAtomicLong(key,redisTemplate.getConnectionFactory());
//设置过期时间
counter.expireAt(expireTime);
return counter.incrementAndGet();
}
}