MySQL 雪花Id函数
作者:mmseoamin日期:2023-12-21

环境 MySQL5.7

简介

snowflake是Twitter开源的分布式ID生成算法,结果是64bit的Long类型的ID,有着全局唯一和有序递增的特点。

MySQL 雪花Id函数,show,第1张

  • 最高位是符号位,因为生成的 ID 总是正数,始终为0,不可用。
  • 41位的时间序列,精确到毫秒级,41位的长度可以使用69年。时间位还有一个很重要的作用是可以根据时间进行排序。
  • 10位的机器标识,10位的长度最多支持部署1024个节点。
  • 12位的计数序列号,序列号即一系列的自增ID,可以支持同一节点同一毫秒生成多个ID序号,12位的计数序列号支持每个节点每毫秒产生4096个ID序号。

    缺点也是有的,就是强依赖机器时钟,如果机器上时钟回拨,有可能会导致主键重复的问题。

    雪花Id

    脚本根据 github:https://github.com/yitter/IdGenerator/tree/master/SQL 的SQL Server 版移植而来

    雪花Id脚本

    CREATE FUNCTION `SnowId`() RETURNS bigint(20)
    BEGIN
    	
    	DECLARE b_current_time BIGINT;
    	DECLARE b_time_tick BIGINT;
    	DECLARE i_work_id INT;
    	DECLARE i_work_id_big_length INT;
    	DECLARE i_seq_big_length INT;
    	DECLARE f_random FLOAT;
    	
    	DECLARE b_res BIGINT;
    	
    	SET i_work_id = 1;
    	SET i_work_id_big_length = 4;
    	SET i_seq_big_length = 8;
    	SET b_current_time = (REPLACE(UNIX_TIMESTAMP(CURRENT_TIMESTAMP(3)),'.','')) + 0;
    	SET b_time_tick = b_current_time - 1582136402000;
    	SET f_random = RAND();
    	
    	SET b_res = b_time_tick * POWER(2, i_work_id_big_length + i_seq_big_length) + i_work_id * POWER(2, i_seq_big_length) + (5 + round((POWER(2, i_seq_big_length)-1) * f_random, 0));
    	
    	RETURN b_res;
    END
    

    测试脚本

    创建一个名为TestSnowId存储过程

    内容:

    定义了一个int变量i默认为1;

    创建了一个临时表temp_numbers用于存储生成的SnowId;

    循环5000次,并将SnowId添加到temp_numbers表内;

    查询temp_numbers表内数据;

    删除临时表;

    CREATE PROCEDURE `TestSnowId` () 
    BEGIN
    	DECLARE i INT DEFAULT 1;
    	CREATE TEMPORARY TABLE IF NOT EXISTS temp_numbers ( number BIGINT );
    	WHILE i <= 5000 DO
    	    INSERT INTO temp_numbers ( number ) VALUES (SnowId ());
    		SET i = i + 1;
    	END WHILE;
    	SELECT * FROM temp_numbers;
    	DROP TEMPORARY TABLE IF EXISTS temp_numbers;
    END
    

    使用

    调用语句

    SELECT SnowId();
    

    MySQL 雪花Id函数,getSnowId,第2张

    测试是否重复

    CALL TestSnowId();
    

    MySQL 雪花Id函数,test,第3张