分享一种java实现的业务序列号生成方法

不太完美,供参考,提供一种思路

首先,设计一张序列号表,管理各种序列号

其次,通过java代码实现序列号生成逻辑

java 复制代码
public class GenerateSerialCodeService {

    @Resource
    private VideoSerialCodeService videoSerialCodeService;

    //自增序列号长度
    private static int SELF_INCREASE_NUM_LENGTH = 6;
    //自增序列号步长
    private static int SELF_INCREASE_NUM_STEP = 1;
    //初始化自增序列号
    private static String INIT_INCREASE_NUM = "000001";

    /**
     * 生成年月+编号的Id
     * @param businessType
     * @return
     */
    @Transactional(rollbackFor = Exception.class)
    public String getSerialCode(BusinessTypeEnum businessType){

        String serialCode = "";
        String infix = DateTimeUtil.DATE_FORMAT_yyyyMM.format(new Date());

        List<VideoSerialCodePo> videoSerialCodePoList = queryByBusinessTypeAndInfix(businessType, infix);
        if (CollectionUtils.isNotEmpty(videoSerialCodePoList)){
           //存在当前业务和当前月份的序列号,继续生成序列号:selfIncreaseNum+step; 长度为:numLength;并生成流水号;修改保存到数据库中。
            VideoSerialCodePo videoSerialCodePo = videoSerialCodePoList.get(0);

            Integer currentSelfIncreaseNumInt = Integer.parseInt(videoSerialCodePo.getSelfIncreaseNum())+
                    videoSerialCodePo.getStep();
            String currentSelfIncreaseNumStr = String.valueOf(currentSelfIncreaseNumInt);

            //自增序列号的长度不足numLength属性设置的值时,前面补0
            if (currentSelfIncreaseNumStr.length()<videoSerialCodePo.getNumLength()){
                String selfIncreaseNum = completion0(Long.valueOf(currentSelfIncreaseNumInt),videoSerialCodePo.getNumLength());

                videoSerialCodePo.setSelfIncreaseNum(selfIncreaseNum);
                videoSerialCodePo.setSerialCode(infix+selfIncreaseNum);
            } else{
                //自增序列号的长度比numLength属性设置的值大时,使用当前自增序列号的长度
                videoSerialCodePo.setSelfIncreaseNum(currentSelfIncreaseNumStr);
                videoSerialCodePo.setNumLength(currentSelfIncreaseNumStr.length());
                videoSerialCodePo.setSerialCode(infix+currentSelfIncreaseNumStr);
            }
            videoSerialCodePo.setVersion(videoSerialCodePo.getVersion()+1);
            this.videoSerialCodeService.update(videoSerialCodePo);
            serialCode = videoSerialCodePo.getSerialCode();
        }else {
            //不存在当前业务单或当前月份的序列号,继续生成序列号:00001; 长度为:numLength;并生成流水号;新增保存到数据库中。
            VideoSerialCodePo videoSerialCodePo = VideoSerialCodePo.builder()
                    .prefix(StringUtils.EMPTY)
                    .infix(infix)
                    .selfIncreaseNum(INIT_INCREASE_NUM)
                    .numLength(SELF_INCREASE_NUM_LENGTH)
                    .serialCode(infix+INIT_INCREASE_NUM)
                    .step(SELF_INCREASE_NUM_STEP)
                    .businessType(businessType)
                    .remark(businessType.getDescription())
                    .version(0)
                    .build();
            this.videoSerialCodeService.save(videoSerialCodePo);
            serialCode = videoSerialCodePo.getSerialCode();
        }

        return serialCode;
    }

    /**
     * 数字转字符串 补0
     * @param i
     * @param len
     * @return
     */
    public static String completion0(long i,int len){
        // 得到一个NumberFormat的实例
        NumberFormat nf = NumberFormat.getInstance();
        // 设置是否使用分组
        nf.setGroupingUsed(false);
        // 设置最大整数位数
        nf.setMaximumIntegerDigits(len);
        // 设置最小整数位数
        nf.setMinimumIntegerDigits(len);
        // 输出测试语句
        return nf.format(i);
    }

    /**
     * 根据BusinessTypeAndInfix查询
     * @param businessType
     * @param infix
     * @return
     */
    public List<VideoSerialCodePo> queryByBusinessTypeAndInfix(BusinessTypeEnum businessType, String infix){
        if (Objects.isNull(businessType)|| Objects.isNull(infix)){
            return Lists.newArrayList();
        }
        QueryVideoSerialCodeRequest request = QueryVideoSerialCodeRequest.builder()
                .businessType(businessType)
                .infix(infix)
                .build();
        return videoSerialCodeService.queryByRequestList(request);
    }
}