UniqueID在一个真实的系统里可能也可以承担更多的作用。概括起来主要有以下几点:

唯一性

时间相关

粗略有序

可反解

可制造

下面我分别讲每个作用后面的考虑和权衡,也会对比介绍一下业界已知的几种 ID 设计。

要唯一性,是否需要全局唯一?

说起全局唯一,通常大家都会想到发号器服务,分布式的通常需要更大空间,中心式的则需要在一个合适的地方会聚。这就可能涉及到锁,而锁意味着成本和性能的下降。所以当前的系统是否需要全局的唯一性,就是一个需要考虑的问题。

比如在通讯系统里,聊天消息可能就未必需要全局,因为一条消息只是某一个人发出,系统只要保证一个人维度的唯一性即可。所以IM只需要通过用户ID和时间ID来组成唯一ID就可以了。本质上而言,这里利用了用户 ID 的唯一性,因为唯一性是可以依赖的,通常我们设计系统也都是基于类似的性质。

用时间来做什么?千万年太久,只争朝夕?

前面说到唯一性可以依赖,我们需要选择的是依赖什么。通常的做法可以选择数据库自增,这在很多数据库里都是可以满足ACID 的操作。但是用数据库有个缺点,就是数据库有性能问题,在多机房情况下也很难处理。当然,你可以通过调整自增的步长来设计,但对于一个发号器而言,操作和维护都略重了。

时间是天然唯一的,因此也是很多设计的选择。但对于一个8Byte的 ID 而言,时间并没有那么多。你如果精确到秒级别,三十年都要使用30bit,到毫秒级则要再增加10bit,你也只剩下20bit 可以做其他事情了。之所以在8Byte 上捣鼓,因为8Byte是一个Long,不管在处理器和编译器还是语言层面,都是可以更好地被处理。

然而三十年够么?对于一个人来说,可能不够,但对一个系统而言,可能足够。我们经常开玩笑,互联网里能活三十年的系统有多少呢?三十年过去,你的系统可能都被重写 N 遍了。这样的信心同样来自于摩尔定律,三十年后,计算性能早就提高了上千倍,到时候更多Byte 都不会是问题了。

粗略有多粗略,秒还是毫秒?

每秒一个或者每毫秒一个ID明显是不够的,刚才说到还有20bit可以做其他事情,就包括一个SequenceID。如果要达到精确的有序,就要对 Sequence进行并发控制,性能上肯定会打折。所以经常会有的一个选择就是,在这个秒的级别上不再保证顺序,而整个 ID则只保证时间上的有序。后一秒的 ID肯定比前一秒的大,但同一秒内可能后取的ID比前面的号小。这在使用时非常关键,你要理解,系统也要接受才可以。

那时间用秒还是毫秒呢?其实不用毫秒的时候就可以把空出来的10bit送给 Sequence,但整个ID的精度就下降了。峰值速度是更现实的考虑。Sequence的空间决定了峰值的速度,而峰值也就意味着持续的时间不会太久。这方面,每秒100万比每毫秒1000限制更小。

可反解,解开的是什么?

一个 ID 生成之后,就会伴随着信息终身,排错分析的时候,我们需要查验。这时候一个可反解的 ID 可以帮上很多忙,从哪里来的,什么时候出生的。跟身份证倒有点儿相通了,其实身份证就是一个典型的分布式 ID生成器。

如果ID里已经有了时间而且能解开,在存储层面可能不再需要timestamp一类的字段了。微博的 ID 还有很多业务信息,这个后面会细讲。

可制造,为什么不用UUID?

互联网系统上可用性永远是优先指标。但由于分布式系统的脆弱,网络不稳定或者底层存储系统的不可用,业务系统随时面临着失败。为了给前端更友好的响应,我们需要能尽量容忍失败。比如在存储失败时,可能需要临时导出请求供后续处理,而后续处理时已经离开了当时的时间点,顺序跟其他系统错开了。我们需要制造出这样的ID 以便系统好像一直正常运行一样,可制造的 ID 让你可以控制生产日期,然后继续下面的处理。

另一个重要场景就是数据清洗。这个属于较少遇到,但并不罕见的情况,可能是原来 ID 设计的不合理,也可能由于底层存储的改变,都可能出现。这样一个可制造的 ID 就会带来很多操作层面的便利。

这也是我们不用 UUID 的一个原因。UUID 标准可以保证在某时某地生成,但如果要控制生成一个特定时间的 UUID,可能需要底层库的改动。经验告诉我们,能在上层解决的问题不要透到下层,这种库的维护成本是非常高的。

转自@一乐的http://ericliang.info/what-kind-of-id-generator-we-need-in-business-systems

Unique ID的特性需求分析相关推荐

  1. 生成唯一序列号 Unique ID

    唯一的序列号Unique ID,在程序的各个方面都有所应用,特别是数据存储方面.很多数据库都需要一个自增的唯一的序列号作为Primary Key. 最简单的Unique ID就是在内存中维护一个lon ...

  2. linux mtk unique id,1.2.16.1. Nand Flash的Unique ID

    1.2.16.1.4.1. 读取遵循ONFI的厂商的Nand的Unique ID 如果经过上述判断,此符合ONFI的Nand Flash支持Read Unique ID命令,次此时就可以通过该命令来读 ...

  3. stm32 HAL 获取芯片flash容量和unique ID的方法(检验是否买错芯片)

    在stm32参考手册中可以找到 #1 获取flash 大小 void GetFlashSize(void) {uint16_t Stm32_Flash_Size;Stm32_Flash_Size = ...

  4. Unique ID策略

    下面对比几个典型的Unique ID策略. Redis Redis有 高性能,高并发和数据一致性的保证,以及断电数据不丢失,分布式扩展能力等优势.所以业界普遍使用Redis来存储并持久化序列和业务规则 ...

  5. altium 原理图reset unique id

    当画模块原理图时,电路相同的模块可以单独建一个文件,然后复制粘贴,得到多个相同的原理图图纸 然而sheet文件复制粘贴会出现ID相同的情况: UNIQUE ID在原理图和pcb里面相当于元器件的唯一身 ...

  6. 分布式系统中 Unique ID 的生成方法

    一, 问题描述 在分布式系统存在多个 Shard 的场景中, 同时在各个 Shard 插入数据时, 怎么给这些数据生成全局的 unique ID? 在单机系统中 (例如一个 MySQL 实例), un ...

  7. altium 原理图更新UNIQUE ID一样怎么办

    UNIQUE ID在原理图和pcb里面相当于元器件的唯一身份许可,不可相同.有的时候我们操作不当造成ID相同怎么办呢. 在原理图界面,TOOL/convert/RESET PART/SHEET UNI ...

  8. NAND FLASH的ONFI,LBA,UNIQUE ID

    Nand Flash中的ONFI,LBA,Unique ID http://bbs.chinaunix.net/thread-3558530-1-1.html

  9. stm32的unique ID全球唯一码

    我经常把STM32的全球唯一码作为 网卡的MAC地址,但有一天我发现 我发现,我的2个板子 的MAC地址一样,造成只能有一个ping通. 我查看这2个板子的单片机的UNIQUE ID,发现非常接近. ...

最新文章

  1. 律师也要被AI抢“饭碗”了?网友:我还能做什么
  2. Facebook 开源标准卷积替代方案 OctConv
  3. Python练习 | Python中的运算符
  4. c语言电报关系的题目,c语言所有题目以跟答案.doc
  5. 28-hadoop-hbase入门小程序
  6. word2003插入页码
  7. Firefox 2015 最受国人欢迎的十大扩展
  8. anaconda下载速度太慢_Anaconda更新下载速度慢的解决方法:更换源
  9. iOS APP打开微信小程序
  10. html怎么定义403页面,自定义 403 错误页面(示例代码)
  11. XDOJ最长单词的长度
  12. 快递查询方法一键查询物流信息
  13. OpenCASCADE 获取面中心点法向
  14. Java回炉学习(一)
  15. Retrofit+Recycleview+fresco
  16. 12亿次月访问流量网站服务器架构探秘
  17. 【验证码逆向专栏】极验三代、四代点选类验证码逆向分析
  18. 【Cadence16.6—Day3】用Cadence16.6绘制STM32H743最小系统原理图
  19. 内核ioremap接口报Warning问题
  20. 如何判断是在做正确的事?

热门文章

  1. 计算机考研专业课看谁的书,计算机考研专业课视频看谁的
  2. 百科知识 .e,.ec文件如何打开
  3. 计算机考试ASP题目怎么做,ASP学生考试系统
  4. 严格凸函数充分必要条件_关于凸函数的两个充分必要条件
  5. GH6159固溶处理(GH159)时效处理
  6. html--电子闹钟
  7. Golang使用go mod 导入本地库
  8. Linux GRUB启动分析之stage1
  9. onestage方法_目标检测——One-stage和Two-stage的详解
  10. 谷歌插件DHC测试HTTP接口