关注JEECG发展历程 关注最新动态和版本, 记录JEECG成长点滴 更新日志 - 技术支持 - 招聘英才

JEECG最新版本下载 JEECG智能开发平台 - 显著提高开发效率 常见问题 - 入门视频 - 参与开源团队

商务QQ: 69893005、418799587 商务热线(5*8小时): 010-64808099 官方邮箱: jeecgos@163.com

查看: 6651|回复: 0

【Flowable实战】Flowable6.4.1自定义id生成

[复制链接]
发表于 2023-2-18 16:12:04 | 显示全部楼层 |阅读模式
1. 雪花Id生成器
  1. /**
  2. * 雪花算法生成id
  3. * @author
  4. *
  5. */
  6. public class Snowflake {

  7.     private final static long TWEPOCH = 1288834974657L;

  8.     // 机器标识位数
  9.     private final static long WORKER_ID_BITS = 5L;

  10.     // 数据中心标识位数
  11.     private final static long DATA_CENTER_ID_BITS = 5L;

  12.     // 机器ID最大值 31
  13.     private final static long MAX_WORKER_ID = -1L ^ (-1L << WORKER_ID_BITS);

  14.     // 数据中心ID最大值 31
  15.     private final static long MAX_DATA_CENTER_ID = -1L ^ (-1L << DATA_CENTER_ID_BITS);

  16.     // 毫秒内自增位
  17.     private final static long SEQUENCE_BITS = 12L;

  18.     // 机器ID偏左移12位
  19.     private final static long WORKER_ID_SHIFT = SEQUENCE_BITS;

  20.     private final static long DATA_CENTER_ID_SHIFT = SEQUENCE_BITS + WORKER_ID_BITS;

  21.     // 时间毫秒左移22位
  22.     private final static long TIMESTAMP_LEFT_SHIFT = SEQUENCE_BITS + WORKER_ID_BITS + DATA_CENTER_ID_BITS;

  23.     private final static long SEQUENCE_MASK = -1L ^ (-1L << SEQUENCE_BITS);

  24.     private long lastTimestamp = -1L;

  25.     private long sequence = 0L;
  26.     private final long workerId;
  27.     private final long dataCenterId;
  28.     private static volatile Snowflake snowflake = null;
  29.     private static Object lock = new Object();

  30.     //单例禁止new实例化
  31.     private Snowflake(long workerId, long dataCenterId) {
  32.         if (workerId > MAX_WORKER_ID || workerId < 0) {
  33.             workerId = getRandom();
  34.         }

  35.         if (dataCenterId > MAX_DATA_CENTER_ID || dataCenterId < 0) {

  36.             throw new IllegalArgumentException(String.format("%s 数据中心ID最大值 必须是 %d 到 %d 之间", dataCenterId, 0, MAX_DATA_CENTER_ID));
  37.         }
  38.         this.workerId = workerId;
  39.         this.dataCenterId = dataCenterId;
  40.     }

  41.     /**
  42.      * 获取单列
  43.      *
  44.      * @return
  45.      */
  46.     public static Snowflake getInstanceSnowflake() {
  47.         if (snowflake == null) {
  48.             synchronized (lock) {
  49.                 long workerId ;
  50.                 long dataCenterId = getRandom();
  51.                 try {
  52.                     //第一次使用获取mac地址的
  53.                     workerId = getWorkerId();
  54.                 } catch (Exception e) {
  55.                     workerId = getRandom();
  56.                 }
  57.                 snowflake = new Snowflake(workerId, dataCenterId);
  58.             }
  59.         }
  60.         return snowflake;
  61.     }

  62.     /**
  63.      * 生成1-31之间的随机数
  64.      *
  65.      * @return
  66.      */
  67.     private static long getRandom() {
  68.         int max = (int) (MAX_WORKER_ID);
  69.         int min = 1;
  70.         Random random = new Random();
  71.         long result = random.nextInt(max - min) + min;
  72.         return result;
  73.     }

  74.     public static String getSnowflakeId() throws Exception{
  75.         return Snowflake.getInstanceSnowflake().nextId()+"";
  76.     }

  77.     private synchronized long nextId() throws Exception {
  78.         long timestamp = time();
  79.         if (timestamp < lastTimestamp) {
  80.             throw new Exception("时钟向后移动,拒绝生成id  " + (lastTimestamp - timestamp) + " milliseconds");
  81.         }

  82.         if (lastTimestamp == timestamp) {
  83.             // 当前毫秒内,则+1
  84.             sequence = (sequence + 1) & SEQUENCE_MASK;
  85.             if (sequence == 0) {
  86.                 // 当前毫秒内计数满了,则等待下一秒
  87.                 timestamp = tilNextMillis(lastTimestamp);
  88.             }
  89.         } else {
  90.             sequence = 0;
  91.         }
  92.         lastTimestamp = timestamp;

  93.         // ID偏移组合生成最终的ID,并返回ID
  94.         long nextId = ((timestamp - TWEPOCH) << TIMESTAMP_LEFT_SHIFT)
  95.                 | (dataCenterId << DATA_CENTER_ID_SHIFT) | (workerId << WORKER_ID_SHIFT) | sequence;

  96.         return nextId;
  97.     }

  98.     private long tilNextMillis(final long lastTimestamp) {
  99.         long timestamp = this.time();
  100.         while (timestamp <= lastTimestamp) {
  101.             timestamp = this.time();
  102.         }
  103.         return timestamp;
  104.     }

  105.     private long time() {
  106.         return System.currentTimeMillis();
  107.     }

  108.     @SuppressWarnings("Duplicates")
  109.     private static long getWorkerId() throws SocketException, UnknownHostException, NullPointerException {
  110.         @SuppressWarnings("unused")
  111.         InetAddress ip = InetAddress.getLocalHost();

  112.         NetworkInterface network = null;
  113.         Enumeration<NetworkInterface> en = NetworkInterface.getNetworkInterfaces();
  114.         while (en.hasMoreElements()) {
  115.             NetworkInterface nint = en.nextElement();
  116.             if (!nint.isLoopback() && nint.getHardwareAddress() != null) {
  117.                 network = nint;
  118.                 break;
  119.             }
  120.         }

  121.         @SuppressWarnings("ConstantConditions")
  122.         byte[] mac = network.getHardwareAddress();

  123.         Random rnd = new Random();
  124.         byte rndByte = (byte) (rnd.nextInt() & 0x000000FF);

  125.         // 取mac地址最后一位和随机数
  126.         return ((0x000000FF & (long) mac[mac.length - 1]) | (0x0000FF00 & (((long) rndByte) << 8))) >> 6;
  127.     }


  128.     public static void main(String[] args) {
  129.         long start = System.currentTimeMillis();
  130.         try {
  131.             for (int i = 0, len = 1000000; i < len; i++) {
  132.                 //getSnowflakeId();
  133.                 System.out.println(getSnowflakeId());
  134.             }
  135.         } catch (Exception e) {

  136.         }
  137.         System.out.println("100万耗时: " + (System.currentTimeMillis()-start) + "ms");

  138.     }
  139. }
复制代码



2. 实现接口重写方法
  1. @Configuration
  2. public class FlowableConfiguration implements EngineConfigurationConfigurer<SpringProcessEngineConfiguration>
  3. {
  4.     @Override
  5.     public void configure(SpringProcessEngineConfiguration springProcessEngineConfiguration) {
  6.         springProcessEngineConfiguration.setIdGenerator(new IdGenerator() {
  7.             @Override
  8.             public String getNextId() {
  9.                 try {
  10.                     return Snowflake.getSnowflakeId(); //id生成方法
  11.                 }catch (Exception e) {
  12.                 }
  13.                 return null;
  14.             }
  15.         });
  16.     }
  17. }
复制代码


3. 完成



您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

快速回复 返回顶部 返回列表