分布式 ID 的首要目标是唯一,不是“看起来随机”。选型前还要明确是否需要按时间大致递增、是否隐藏业务规模、数据库索引是否敏感,以及中心服务失效时能否继续发号。
Table of contents
Open Table of contents
四类方案怎么选
| 方案 | 优点 | 主要代价 |
|---|---|---|
| UUID v4 | 无中心、生成简单 | 128 位且随机,B+Tree 写入局部性差 |
| Snowflake | 64 位、趋势递增、本地生成 | 依赖时钟和唯一节点号 |
| 数据库号段 | 连续区间批量领取,吞吐稳定 | 依赖发号存储,客户端需双缓冲 |
| CosId 等组件 | 封装节点分配与号段能力 | 仍要理解配置、存储和故障边界 |
“趋势递增”表示总体随时间增长,同一毫秒内由序列号区分;它不保证跨节点严格连续。不要把 ID 差值当成订单量,也不要要求删除后补洞。
拆开 Snowflake
经典布局把 64 位分给时间戳、节点号和毫秒内序号。位数决定硬上限:10 位节点号最多 1024 个节点,12 位序号每节点每毫秒最多 4096 个 ID。
在分布式系统实验室下载运行:
mvn -Dtest=DistributedMechanismsTest#snowflakeIdsIncreaseAndQuorumRequiresMajority test
示例向生成器注入 Clock,因此测试可固定时间并验证序号递增。实现检测到时钟回拨会失败关闭(fail closed),避免生成重复 ID。生产策略还可等待小幅回拨、切换备用节点号或使用逻辑时钟,但必须监控回拨次数和等待时间。
架构验收清单
- 压测峰值每毫秒发号量,并留增长余量。
- 证明节点号不会因容器重建而重复。
- 演练 NTP 校时、时钟回拨和发号存储不可用。
- 用无符号/有符号与 JSON 数字边界检查跨语言兼容。
- 业务外部 ID 需要防枚举时,另加不可猜测标识,不要牺牲内部主键性能。
下一步
继续阅读08-04 ZooKeeper 数据模型、会话与 Watch,进入第一个真实协调系统。