惯性聚合 高效追踪和阅读你感兴趣的博客、新闻、科技资讯
阅读原文 在惯性聚合中打开

推荐订阅源

博客园_首页
Exploit-DB.com RSS Feed
Exploit-DB.com RSS Feed
P
Proofpoint News Feed
G
Google Developers Blog
B
Blog
Engineering at Meta
Engineering at Meta
阮一峰的网络日志
阮一峰的网络日志
The Register - Security
The Register - Security
奇客Solidot–传递最新科技情报
奇客Solidot–传递最新科技情报
博客园 - 叶小钗
The Cloudflare Blog
The Hacker News
The Hacker News
D
Darknet – Hacking Tools, Hacker News & Cyber Security
C
CXSECURITY Database RSS Feed - CXSecurity.com
雷峰网
雷峰网
F
Fortinet All Blogs
钛媒体:引领未来商业与生活新知
钛媒体:引领未来商业与生活新知
H
Hackread – Cybersecurity News, Data Breaches, AI and More
酷 壳 – CoolShell
酷 壳 – CoolShell
Last Week in AI
Last Week in AI
T
Threat Research - Cisco Blogs
A
About on SuperTechFans
量子位
Recorded Future
Recorded Future
博客园 - 三生石上(FineUI控件)
H
Help Net Security
Help Net Security
Help Net Security
P
Palo Alto Networks Blog
cs.CV updates on arXiv.org
cs.CV updates on arXiv.org
T
Troy Hunt's Blog
W
WeLiveSecurity
V
Vulnerabilities – Threatpost
T
The Exploit Database - CXSecurity.com
Know Your Adversary
Know Your Adversary
Apple Machine Learning Research
Apple Machine Learning Research
Scott Helme
Scott Helme
N
News | PayPal Newsroom
AWS News Blog
AWS News Blog
D
DataBreaches.Net
Blog — PlanetScale
Blog — PlanetScale
MongoDB | Blog
MongoDB | Blog
B
Blog RSS Feed
腾讯CDC
J
Java Code Geeks
Microsoft Azure Blog
Microsoft Azure Blog
TaoSecurity Blog
TaoSecurity Blog
GbyAI
GbyAI
Y
Y Combinator Blog
Hacker News - Newest:
Hacker News - Newest: "LLM"
D
Docker

iyear - 记录本是反抗 - iyear

LFX Mentorship: 与 KubeVela 社区在开源相遇 - iyear OSPP2022 + DevStream社区 复盘 - iyear 《图解TCP/IP》读后感 - iyear - 记录本是反抗 Redis · 为什么哈希槽数为16384? - iyear 3200元32G1TSSD开发机DIY选型经历 - iyear - 记录本是反抗 企鹅电竞WebSocket弹幕协议浅析 - iyear - 记录本是反抗 2021 - iyear - 记录本是反抗 在N1小钢炮上搭建私有音乐库koel - iyear - 记录本是反抗 尝试理解前后端分离 - iyear - 记录本是反抗
分布式 · 一致性哈希 - iyear
博主: iyear · 2022-04-15 · via iyear - 记录本是反抗 - iyear

分布式 · 一致性哈希

  • 发布时间:
  • 6527次浏览
  • 6 条评论
  • 2420字数
  • 分类: 技术研究
  1. 首页
  2. 正文  

缘由:Kitex文档的一致性哈希实现负载均衡,好吧,我连什么是一致性哈希都不知道

一、传统哈希取模算法的局限性

1.1 节点增加、减少

任何节点的故障或临时增加我们都只希望性能上有所降低,而不是服务受到影响。

对于传统哈希算法,节点的增加、减少会导致键与节点的映射关系发生变化。对于已有的键来说,将导致节点映射错误。

1.2 结论

当集群中节点的数量发生变化时,之前的映射规则就可能发生变化。

对于分布式缓存,映射规则失效意味着之前缓存的失效,若同一时刻出现大量的缓存失效,则可能会出现 “缓存雪崩”,这将会造成灾难性的后果。

要解决此问题,我们必须在其余节点上重新分配所有现有键,这是非常昂贵的操作,并且可能对正在运行的系统产生不利影响。

二、一致性哈希算法

Wiki: https://zh.wikipedia.org/wiki/%E4%B8%80%E8%87%B4%E5%93%88%E5%B8%8C

一致性哈希算法是在哈希算法基础上提出的

哈希算法应该满足的几个条件:

  • 平衡性:是指 Hash 的结果应该平均分配到各个节点
  • 单调性:是指在新增或者删减节点时,不影响系统正常运行
  • 分散性:是指数据应该分散地存放在分布式集群中的各个节点(节点自己可以有备份),不必每个节点都存储所有的数据

2.1 对象、服务器哈希

通过一致性哈希环(Hash Ring)实现。这个环的起点是 0,终点是 2^32 - 1,并且起点与终点连接,故这个环的整数分布范围是 [0, 2^32-1]

其实终点可以自定义,或许这个数字来源为IP地址为32位

点由哈希函数再取模得出

k1 k2 k3 k4 为四个对象哈希后的位置

t1 t2 t3 为三个服务器哈希后的位置,可以选择服务器的IP或主机名等等作为键

2.2 映射规则

将对象和服务器都放置到同一个哈希环后,在哈希环上顺时针查找距离这个对象的 hash 值最近的机器,即是这个对象所属的机器。

o2 对象为例,顺序针找到最近的机器是 cs2,故服务器 cs2 会缓存 o2 对象。

而服务器 cs1 则缓存 o1o3 对象,

服务器 cs3 则缓存 o4 对象。

2.3 服务器增加

假设由于业务需要,我们需要增加一台服务器 cs4

经过同样的 hash 运算,该服务器最终落于 t1t2 服务器之间

可见,只有 t1t2 之间的对象需要重新分配

2.4 服务器减少

假设 cs3 服务器出现故障导致服务下线

可见,只有 t2t3 之间的对象需要重新分配

2.5 数据倾斜与解决方案

当物理节点数量较少时,一致性哈希的平衡性是有问题的

  1. 某些节点承担的 key 非常多,一些节点却非常少。一旦负载较多的物理节点挂了,容易造成缓存雪崩
  2. 纯物理节点无法实现权重分配

我们可以创造出一组虚拟节点,再让虚拟节点向物理节点映射,解决了以上两点

虚拟节点数越大,内存和计算代价越大,负载越均衡

Kitex 的文档中

推荐 VirtualFactor * Weight(如果 Weighted 为 true)的中位数在 1000 左右,负载应当已经很均衡了

推荐 总虚拟节点数 在 2000W 以内(1000W 情况之下 build 一次需要 250ms,不过为后台 build 理论上 3s 内均无问题)

2.6 依旧存在的缺点

  • 哈希环结构的存在,无法手动管理和精细化控制
  • 哈希环上的虚拟节点非常多或者更新频繁时,查找和迁移计算性能会比较低下

Redis 作为著名的分布式缓存系统,其 Sharding 采用的并不是一致性哈希,而是哈希槽,在一定程度上解决了以上问题

开源库实现

参考

相关文章实在是太多了

  1. https://segmentfault.com/a/1190000021199728
  2. https://zhuanlan.zhihu.com/p/98030096
  3. https://juejin.cn/post/7064557796762583047
  4. https://juejin.cn/post/6844903670430040078

分布式 · 一致性哈希

 • 

缘由:Kitex文档的一致性哈希实现负载均衡,好吧,我连什么是一致性哈希都不知道

一、传统哈希取模算法的局限性

1.1 节点增加、减少

任何节点的故障或临时增加我们都只希望性能上有所降低,而不是服务受到影响。

对于传统哈希算法,节点的增加、减少会导致键与节点的映射关系发生变化。对于已有的键来说,将导致节点映射错误。

1.2 结论

当集群中节点的数量发生变化时,之前的映射规则就可能发生变化。

对于分布式缓存,映射规则失效意味着之前缓存的失效,若同一时刻出现大量的缓存失效,则可能会出现 “缓存雪崩”,这将会造成灾难性的后果。

要解决此问题,我们必须在其余节点上重新分配所有现有键,这是非常昂贵的操作,并且可能对正在运行的系统产生不利影响。

二、一致性哈希算法

Wiki: https://zh.wikipedia.org/wiki/%E4%B8%80%E8%87%B4%E5%93%88%E5%B8%8C

一致性哈希算法是在哈希算法基础上提出的

哈希算法应该满足的几个条件:

  • 平衡性:是指 Hash 的结果应该平均分配到各个节点
  • 单调性:是指在新增或者删减节点时,不影响系统正常运行
  • 分散性:是指数据应该分散地存放在分布式集群中的各个节点(节点自己可以有备份),不必每个节点都存储所有的数据

2.1 对象、服务器哈希

通过一致性哈希环(Hash Ring)实现。这个环的起点是 0,终点是 2^32 - 1,并且起点与终点连接,故这个环的整数分布范围是 [0, 2^32-1]

其实终点可以自定义,或许这个数字来源为IP地址为32位

点由哈希函数再取模得出

k1 k2 k3 k4 为四个对象哈希后的位置

t1 t2 t3 为三个服务器哈希后的位置,可以选择服务器的IP或主机名等等作为键

2.2 映射规则

将对象和服务器都放置到同一个哈希环后,在哈希环上顺时针查找距离这个对象的 hash 值最近的机器,即是这个对象所属的机器。

o2 对象为例,顺序针找到最近的机器是 cs2,故服务器 cs2 会缓存 o2 对象。

而服务器 cs1 则缓存 o1o3 对象,

服务器 cs3 则缓存 o4 对象。

2.3 服务器增加

假设由于业务需要,我们需要增加一台服务器 cs4

经过同样的 hash 运算,该服务器最终落于 t1t2 服务器之间

可见,只有 t1t2 之间的对象需要重新分配

2.4 服务器减少

假设 cs3 服务器出现故障导致服务下线

可见,只有 t2t3 之间的对象需要重新分配

2.5 数据倾斜与解决方案

当物理节点数量较少时,一致性哈希的平衡性是有问题的

  1. 某些节点承担的 key 非常多,一些节点却非常少。一旦负载较多的物理节点挂了,容易造成缓存雪崩
  2. 纯物理节点无法实现权重分配

我们可以创造出一组虚拟节点,再让虚拟节点向物理节点映射,解决了以上两点

虚拟节点数越大,内存和计算代价越大,负载越均衡

Kitex 的文档中

推荐 VirtualFactor * Weight(如果 Weighted 为 true)的中位数在 1000 左右,负载应当已经很均衡了

推荐 总虚拟节点数 在 2000W 以内(1000W 情况之下 build 一次需要 250ms,不过为后台 build 理论上 3s 内均无问题)

2.6 依旧存在的缺点

  • 哈希环结构的存在,无法手动管理和精细化控制
  • 哈希环上的虚拟节点非常多或者更新频繁时,查找和迁移计算性能会比较低下

Redis 作为著名的分布式缓存系统,其 Sharding 采用的并不是一致性哈希,而是哈希槽,在一定程度上解决了以上问题

开源库实现

参考

相关文章实在是太多了

  1. https://segmentfault.com/a/1190000021199728
  2. https://zhuanlan.zhihu.com/p/98030096
  3. https://juejin.cn/post/7064557796762583047
  4. https://juejin.cn/post/6844903670430040078