冰河开源了全网首个完全开源的分布式全局有序序列号(分布式ID)框架!!
针对最近很多人都在面试,我这边也整理了相当多的面试专题资料,也有其他大厂的面经。希望可以帮助到大家。上述的面试题答案都整理成文档笔记。也还整理了一些面试资料&最新2021收集的一些大厂的面试真题(都整理成文档,小部分截图)以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持。《一线大厂Java面试题解析+核心总结学习笔记+最新讲解视频+实战项目源码》点击传送门即可获取!” />针对
1. 序列号
最大峰值型
20位,理论上每秒内平均可产生2^20= 1048576个ID,百万级别,如果系统的网络IO和CPU足够强大,可承受的峰值达到每毫秒百万级别。
最小粒度型
10位,每毫秒内序列号总计2^10=1024个, 也就是每个毫秒最多产生1000+个ID,理论上承受的峰值完全不如我们最大峰值方案。
2. 秒级时间/毫秒级时间
最大峰值型
30位,表示秒级时间,2^30/60/60/24/365=34,也就是可使用30+年。
最小粒度型
40位,表示毫秒级时间,2^40/1000/60/60/24/365=34,同样可以使用30+年。
3. 机器ID
10位, 2^10=1024, 也就是最多支持1000+个服务器。中心发布模式和REST发布模式一般不会有太多数量的机器,按照设计每台机器TPS 1万/s,10台服务器就可以有10万/s的TPS,基本可以满足大部分的业务需求。
但是考虑到我们在业务服务可以使用内嵌发布方式,对机器ID的需求量变得更大,这里最多支持1024个服务器。
4. 生成方式
2位,用来区分三种发布模式:嵌入发布模式,RPC发布模式,REST发布模式。
00:嵌入发布模式
01:RPC发布模式
02:REST发布模式
03:保留未用
5. 序列号类型
1位,用来区分两种ID类型:最大峰值型和最小粒度型。
0:最大峰值型
1:最小粒度型
6. 版本
1位,用来做扩展位或者扩容时候的临时方案。
0:默认值,以免转化为整型再转化回字符串被截断
1:表示扩展或者扩容中
作为30年后扩展使用,或者在30年后ID将近用光之时,扩展为秒级时间或者毫秒级时间来挣得系统的移植时间窗口,其实只要扩展一位,完全可以再使用30年。
并发处理
对于中心服务器和REST发布方式,ID生成的过程涉及到网络IO和CPU操作,ID的生成基本都是内存到高速缓存的操作,没有IO操作,网络IO是系统的瓶颈。
相对于CPU计算速度来说网络IO是瓶颈,因此,ID产生的服务使用多线程的方式,对于ID生成过程中的竞争点time和sequence,这里使用了多种实现方式
- 使用concurrent包的ReentrantLock进行互斥,这是缺省的实现方式,也是追求性能和稳定两个目标的妥协方案。
- 使用传统的synchronized进行互斥,这种方式的性能稍微逊色一些,通过传入JVM参数-Dmykit.serial.sync.lock.impl.key=true来开启。
- 使用CAS方式进行互斥,这种实现方式的性能非常高,但是在高并发环境下CPU负载会很高,通过传入JVM参数-Dmykit.serial.atomic.impl.key=true来开启。
机器ID的分配
我们将机器ID分为两个区段,一个区段服务于RPC发布模式和REST发布模式,另外一个区段服务于嵌入发布模式。
0-923:嵌入发布模式,预先配置,(或者由Zookeeper产生),最多支持924台内嵌服务器
924 – 1023:中心服务器发布模式和REST发布模式,最多支持300台,最大支持300*1万=300万/s的TPS
如果嵌入式发布模式和RPC发布模式以及REST发布模式的使用量不符合这个比例,我们可以动态调整两个区间的值来适应。
另外,各个垂直业务之间具有天生的隔离性,每个业务都可以使用最多1024台服务器。
与Zookeeper集成
对于嵌入发布模式,服务启动需要连接Zookeeper集群,Zookeeper分配一个0-923区间的一个ID,如果0-923区间的ID被用光,Zookeeper会分配一个大于923的ID,这种情况,拒绝启动服务。
如果不想使用Zookeeper产生的唯一的机器ID,我们提供缺省的预配的机器ID解决方案,每个使用统一分布式全局序列号(分布式ID)服务的服务需要预先配置一个默认的机器ID。
时间同步
使用mykit-serial生成分布式全局序列号(分布式ID)时,需要我们保证服务器的时间正常。此时,我们可以使用Linux的定时任务crontab,定时通过授时服务器虚拟集群(全球有3000多台服务器)来核准服务器的时间。
ntpdate -u pool.ntp.orgpool.ntp.org
最终的性能验证要保证每台服务器的TPS达到1万/s以上。
产生分布式全局序列号
-
描述:根据系统时间产生一个全局唯一的全局序列号并且在方法体内返回。
-
路径:/genSerialNumber
-
参数:N/A
-
非空参数:N/A
-
示例:http://localhost:8080/genSerialNumber
-
结果:3456526092514361344
反解全局序列号
-
描述:对产生的serialNumber进行反解,在响应体内返回反解的JSON字符串。
-
路径:/expSerialNumber
-
参数:serialNumber=?
-
非空参数:serialNumber
-
示例:http://localhost:8080/expSerialNumber?serialNumber=3456526092514361344
-
结果:{“genMethod”:2,“machine”:1022,“seq”:0,“time”:12758739,“type”:0,“version”:0}
翻译时间
-
描述:把长整型的时间转化成可读的格式。
-
路径:/transtime
-
参数:time=?
-
非空参数:time
-
示例:http://localhost:8080/transtime?time=12758739
-
结果:Thu May 28 16:05:39 CST 2015
制造全局序列号
-
描述:通过给定的分布式全局序列号元素制造分布式全局序列号。
-
路径:/makeSerialNumber
-
参数:genMethod=?&machine=?&seq=?&time=?&type=?&version=?
-
非空参数:time,seq
-
示例:http://localhost:8080/makeSerialNumber?genMethod=2&machine=1022&seq=0&time=12758739&type=0&version=0
-
结果:3456526092514361344
产生全局序列号
-
描述:根据系统时间产生一个全局唯一的分布式序列号(分布式ID)并且在方法体内返回。
-
类:SerialNumberService
-
方法:genSerialNumber
-
参数:N/A
-
返回类型:long
-
示例:long serialNumber= serialNumberService.genSerialNumber();
反解全局序列号
-
描述:对产生的分布式序列号(分布式ID)进行反解,在响应体内返回反解的JSON字符串。
-
类:SerialNumberService
-
方法:expSerialNumber
-
参数:long serialNumber
-
返回类型:SerialNumber
-
示例:SerialNumber serialNumber = serialNumberService.expSerialNumber(3456526092514361344);
翻译时间
-
描述:把长整型的时间转化成可读的格式。
-
类:SerialNumberService
-
方法:transTime
-
参数:long time
-
返回类型:Date
-
示例:Date date = serialNumberService.transTime(12758739);
制造全局序列号(1)
-
描述:通过给定的分布式序列号元素制造分布式序列号。
-
类:SerialNumberService
-
方法:makeSerialNumber
-
参数:long time, long seq
-
返回类型:long
-
示例:long serialNumber= SerialNumberService.makeSerialNumber(12758739, 0);
制造全局序列号(2)
-
描述:通过给定的ID元素制造ID。
-
类:SerialNumberService
-
方法:makeSerialNumber
-
参数:long machine, long time, long seq
-
返回类型:long
-
示例:long serialNumber= serialNumberService.makeSerialNumber(1, 12758739, 0);
制造全局序列号(3)
-
描述:通过给定的分布式序列号元素制造ID。
-
类:SerialNumberService
-
方法:makeSerialNumber
-
参数:long genMethod, long machine, long time, long seq
-
返回类型:long
-
示例:long serialNumber= serialNumberService.makeSerialNumber(0, 1, 12758739, 0);
制造全局序列号(4)
-
描述:通过给定的分布式序列号元素制造ID。
-
类:SerialNumberService
-
方法:makeSerialNumber
-
参数:long type, long genMethod, long machine, long time, long seq
-
返回类型:long
-
示例:long serialNumber= serialNumberService.makeSerialNumber(0, 2, 1, 12758739, 0);
制造全局序列号(5)
-
描述:通过给定的ID元素制造ID。
-
类:SerialNumberService
-
方法:makeSerialNumber
-
参数:long version, long type, long genMethod, long machine, long time, long seq
-
返回类型:long
-
示例:long serialNumber = serialNumberService.makeSerialNumber(0, 0, 2, 1, 12758739, 0);
自我介绍一下,小编13年上海交大毕业,曾经在小公司待过,也去过华为、OPPO等大厂,18年进入阿里一直到现在。
深知大多数Java工程师,想要提升技能,往往是自己摸索成长或者是报班学习,但对于培训机构动则几千的学费,着实压力不小。自己不成体系的自学效果低效又漫长,而且极易碰到天花板技术停滞不前!
因此收集整理了一份《2024年Java开发全套学习资料》,初衷也很简单,就是希望能够帮助到想自学提升又不知道该从何学起的朋友,同时减轻大家的负担。
既有适合小白学习的零基础资料,也有适合3年以上经验的小伙伴深入学习提升的进阶课程,基本涵盖了95%以上Java开发知识点,真正体系化!
由于文件比较大,这里只是将部分目录截图出来,每个节点里面都包含大厂面经、学习笔记、源码讲义、实战项目、讲解视频,并且会持续更新!
如果你觉得这些内容对你有帮助,可以扫码获取!!(备注Java获取)
最后
针对最近很多人都在面试,我这边也整理了相当多的面试专题资料,也有其他大厂的面经。希望可以帮助到大家。
上述的面试题答案都整理成文档笔记。 也还整理了一些面试资料&最新2021收集的一些大厂的面试真题(都整理成文档,小部分截图)
以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持。
《一线大厂Java面试题解析+核心总结学习笔记+最新讲解视频+实战项目源码》,点击传送门即可获取!
.cn/images/e5c14a7895254671a72faed303032d36.jpg" alt=“img” style=“zoom: 33%;” />
最后
针对最近很多人都在面试,我这边也整理了相当多的面试专题资料,也有其他大厂的面经。希望可以帮助到大家。
[外链图片转存中…(img-DPlmPccb-1712326904015)]
上述的面试题答案都整理成文档笔记。 也还整理了一些面试资料&最新2021收集的一些大厂的面试真题(都整理成文档,小部分截图)
[外链图片转存中…(img-uwx5ubC3-1712326904016)]
以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持。
《一线大厂Java面试题解析+核心总结学习笔记+最新讲解视频+实战项目源码》,点击传送门即可获取!
更多推荐
所有评论(0)