【Gossip 协议】Redis 集群中节点之间的通信方式?

news/2025/3/11 8:55:01/文章来源:https://www.cnblogs.com/o-O-oO/p/18671847

# 分布式系统 # Gossip 协议

在分布式系统中,不同的节点进行数据/信息共享是一个基本的需求。

一种比较简单粗暴的方法就是 集中式发散消息,简单来说就是一个主节点同时共享最新信息给其他所有节点,比较适合中心化系统。这种方法的缺陷也很明显,节点多的时候不光同步消息的效率低,还太依赖与中心节点,存在单点风险问题。

于是,分散式发散消息 的 Gossip 协议 就诞生了。

Gossip 协议介绍

Gossip 直译过来就是闲话、流言蜚语的意思。流言蜚语有什么特点呢?容易被传播且传播速度还快,你传我我传他,然后大家都知道了。

Gossip 协议 也叫 Epidemic 协议(流行病协议)或者 Epidemic propagation 算法(疫情传播算法),别名很多。不过,这些名字的特点都具有 随机传播特性 (联想一下病毒传播、癌细胞扩散等生活中常见的情景),这也正是 Gossip 协议最主要的特点。

Gossip 协议最早是在 ACM 上的一篇 1987 年发表的论文 《Epidemic Algorithms for Replicated Database Maintenance》中被提出的。根据论文标题,我们大概就能知道 Gossip 协议当时提出的主要应用是在分布式数据库系统中各个副本节点同步数据。

正如 Gossip 协议其名一样,这是一种随机且带有传染性的方式将信息传播到整个网络中,并在一定时间内,使得系统内的所有节点数据一致。

在 Gossip 协议下,没有所谓的中心节点,每个节点周期性地随机找一个节点互相同步彼此的信息,理论上来说,各个节点的状态最终会保持一致。

下面我们来对 Gossip 协议的定义做一个总结:
Gossip 协议是一种允许在分布式系统中共享状态的去中心化通信协议,通过这种通信协议,我们可以将信息传播给网络或集群中的所有成员。

Gossip 协议应用

NoSQL 数据库 Redis 和 Apache Cassandra、服务网格解决方案 Consul 等知名项目都用到了 Gossip 协议,学习 Gossip 协议有助于我们搞清很多技术的底层原理。

我们这里以 Redis Cluster 为例说明 Gossip 协议的实际应用。

我们经常使用的分布式缓存 Redis 的官方集群解决方案(3.0 版本引入) Redis Cluster 就是基于 Gossip 协议来实现集群中各个节点数据的最终一致性。

【图】Redis 的官方集群解决方案

Redis Cluster 是一个典型的分布式系统,分布式系统中的各个节点需要互相通信。既然要相互通信就要遵循一致的通信协议,Redis Cluster 中的各个节点基于 Gossip 协议 来进行通信共享信息,每个 Redis 节点都维护了一份集群的状态信息。

Redis Cluster 的节点之间会相互发送多种 Gossip 消息:

MEET:在 Redis Cluster 中的某个 Redis 节点上执行 CLUSTER MEET ip port 命令,可以向指定的 Redis 节点发送一条 MEET 信息,用于将其添加进 Redis Cluster 成为新的 Redis 节点。

PING/PONG:Redis Cluster 中的节点都会定时地向其他节点发送 PING 消息,来交换各个节点状态信息,检查各个节点状态,包括在线状态、疑似下线状态 PFAIL 和已下线状态 FAIL。

FAIL:Redis Cluster 中的节点 A 发现 B 节点 PFAIL ,并且在下线报告的有效期限内集群中半数以上的节点将 B 节点标记为 PFAIL,节点 A 就会向集群广播一条 FAIL 消息,通知其他节点将故障节点 B 标记为 FAIL 。
……

下图就是主从架构的 Redis Cluster 的示意图,图中的虚线代表的就是各个节点之间使用 Gossip 进行通信 ,实线表示主从复制。

有了 Redis Cluster 之后,不需要专门部署 Sentinel 集群服务了。Redis Cluster 相当于是内置了 Sentinel 机制,Redis Cluster 内部的各个 Redis 节点通过 Gossip 协议共享集群内信息。

cluster.h 文件中定义了所有的消息类型(源码地址:https://github.com/redis/redis/blob/7.0/src/cluster.h) 。Redis 3.0 版本的时候只有 9 种消息类型,到了 7.0 版本的时候已经有 11 种消息类型了。

cluster.h 文件中定义了消息结构 clusterMsg(源码地址:https://github.com/redis/redis/blob/7.0/src/cluster.h) :

clusterMsgData 是一个联合体(union),可以为 PING,MEET,PONG 、FAIL 等消息类型。当消息为 PING、MEET 和 PONG 类型时,都是 ping 字段是被赋值的,这也就解释了为什么我们上面说 PING 、 PONG 和 MEET 实际上是同一种消息。

Gossip 协议消息传播模式

Gossip 设计了两种可能的消息传播模式:反熵(Anti-Entropy) 和 传谣(Rumor-Mongering)。

反熵(Anti-entropy)

根据维基百科:

熵的概念最早起源于物理学,用于度量一个热力学系统的混乱程度。熵最好理解为不确定性的量度而不是确定性的量度,因为越随机的信源的熵越大。

在这里,你可以把反熵中的熵理解为节点之间数据的混乱程度/差异性,反熵就是指消除不同节点中数据的差异,提升节点间数据的相似度,从而降低熵值。

具体是如何反熵的呢?集群中的节点,每隔段时间就随机选择某个其他节点,然后通过互相交换自己的所有数据来消除两者之间的差异,实现数据的最终一致性。

在实现反熵的时候,主要有推、拉和推拉三种方式:

推方式,就是将自己的所有副本数据,推给对方,修复对方副本中的熵。

拉方式,就是拉取对方的所有副本数据,修复自己副本中的熵。

推拉,就是同时修复自己副本和对方副本中的熵。

伪代码如下:

【图】反熵伪代码

在我们实际应用场景中,一般不会采用随机的节点进行反熵,而是可以设计成一个闭环。这样的话,我们能够在一个确定的时间范围内实现各个节点数据的最终一致性,而不是基于随机的概率。
像 InfluxDB 就是这样来实现反熵的。

  1. 节点 A 推送数据给节点 B,节点 B 获取到节点 A 中的最新数据。
    
  2. 节点 B 推送数据给 C,节点 C 获取到节点 A,B 中的最新数据。
    
  3. 节点 C 推送数据给 A,节点 A 获取到节点 B,C 中的最新数据。
    
  4. 节点 A 再推送数据给 B 形成闭环,这样节点 B 就获取到节点 C 中的最新数据。
    

虽然反熵很简单实用,但是,节点过多或者节点动态变化的话,反熵就不太适用了。这个时候,我们想要实现最终一致性就要靠 谣言传播(Rumor mongering) 。

谣言传播(Rumor mongering)

谣言传播指的是分布式系统中的一个节点一旦有了新数据之后,就会变为活跃节点,活跃节点会周期性地联系其他节点向其发送新数据,直到所有的节点都存储了该新数据。

如下图所示(下图来自于INTRODUCTION TO GOSSIP 这篇文章):

【图】Gossip 传播示意图

伪代码如下:

谣言传播比较适合节点数量比较多的情况,不过,这种模式下要尽量避免传播的信息包不能太大,避免网络消耗太大。

总结

反熵(Anti-Entropy)会传播节点的所有数据,而谣言传播(Rumor-Mongering)只会传播节点新增的数据。
我们一般会给反熵设计一个闭环。
谣言传播(Rumor-Mongering)比较适合节点数量比较多或者节点动态变化的场景。

Gossip 协议优势和缺陷

优势:

1、相比于其他分布式协议/算法来说,Gossip 协议理解起来非常简单。

2、能够容忍网络上节点的随意地增加或者减少,宕机或者重启,因为 Gossip 协议下这些节点都是平等的,去中心化的。新增加或者重启的节点在理想情况下最终是一定会和其他节点的状态达到一致。

3、速度相对较快。节点数量比较多的情况下,扩散速度比一个主节点向其他节点传播信息要更快(多播)。

缺陷 :

1、消息需要通过多个传播的轮次才能传播到整个网络中,因此,必然会出现各节点状态不一致的情况。毕竟,Gossip 协议强调的是最终一致,至于达到各个节点的状态一致需要多长时间,谁也无从得知。

2、由于拜占庭将军问题,不允许存在恶意节点。

3、可能会出现消息冗余的问题。由于消息传播的随机性,同一个节点可能会重复收到相同的消息。

总结

Gossip 协议是一种允许在分布式系统中共享状态的通信协议,通过这种通信协议,我们可以将信息传播给网络或集群中的所有成员。
Gossip 协议被 Redis、Apache Cassandra、Consul 等项目应用。
谣言传播(Rumor-Mongering)比较适合节点数量比较多或者节点动态变化的场景。

参考

#一万字详解 Redis Cluster Gossip 协议:
https://segmentfault.com/a/1190000038373546

原创 Guide JavaGuide

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.hqwc.cn/news/869291.html

如若内容造成侵权/违法违规/事实不符,请联系编程知识网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

推荐一款超棒的 Minecraft 启动器:Voxelum/x-minecraft-launcher

X Minecraft Launcher (XMCL) 是一个便于你管理多种整合包、模组、资源包、光影包的现代化启动器。它还支持 Minecraft Forge、 Fabric、Quilt、CurseForge 和 Modrinth它具有以下令人心动的特点:多版本兼容性:支持多个 Minecraft 版本,正式版和愚人节版本。自动化资源下载与…

互联网大中小厂实习面经:滴滴、美团、货拉拉、蔚来、信通院等

本文介绍Momenta、蔚来、中国信息通信研究院、昆仑万维、滴滴、易智瑞等企业各类技术岗位的暑期实习、日常实习面试流程与具体问题~本文介绍Momenta、蔚来、中国信息通信研究院、昆仑万维、滴滴、易智瑞等企业各类技术岗位的暑期实习、日常实习面试流程与具体问题。在前一段时间…

2025年1月买的几个好用的「新物件」

前言 去年底比较忙,换工作+搬家什么的,一堆事情凑在一起,很多24年买的东西还没发开箱 只能后面慢慢补上了,现在先把1月份买的一些东西发一下 红米k80手机 本来我是不想买手机的 不过办了新的套餐,营业厅送了购机补贴,不是很多,所以在补贴范围内选择了「看起来」性价比最…

安卓平板使用can-utils检查can通信功能

安装 termux 打开安卓平板 USB 调试模式,并确保电脑安装了 adb。 下载 termux,通过adb install ./termux.exe安装 termux 到安卓平板。 设置 termux 换源 安装好 termux 后打开,进行换源操作。 termux 中输入termux-change-repo。空格切换选中状态,移动方向键切换选中项目,…

最小系统板五要素

最小系统板五要素 电源在进入芯片的时候需要旁路电容将高频杂散干扰旁路掉VBAT:备用电池 VDD:普通电源 VDDA:ADC信号的电源地VSS:普通地 VSSA:ADC的地晶振给单片机提供时钟脉冲,具体的电容值参考晶振手册??OSC: 外部高速晶振 OSC32: 外部低速晶振复位上电复位和按键复位…

nodecanvas插件的黑魔法:一行代码避免拖拽节点的意外脱离

简介 在nodecanvas造轮子的过程,遇到了鼠标拖拽太快,节点经常会脱离控制的情况。但是nodecanvas却不会有这个问题。 一番折腾发现是nodecanvas调用了GUI.DragWindow(),而我觉得这个函数没啥用给删除了的原因。。 GUI.DragWindow()在MouseDown事件触发时,会调用GrabMouseCon…

windows server2016搭建AD域服务器

windows server2016搭建AD域服务器@目录一、背景二、搭建AD域服务器步骤三、生成可供java程序使用的keystore文件四、导出某用户的keytab文件五、主机配置hosts文件六、主机确认是否能ping通本人其他相关文章链接 一、背景 亲测可用,之前搜索了很多博客,啥样的都有,就是不介绍…

07 异常

什么是异常 异常就像是生活中遇到的意外情况。在程序运行过程中,可能会出现一些意想不到的问题,比如要打开的文件不存在、网络连接突然中断、除数为零等,这些就是异常。当异常发生时,如果不处理,程序可能会崩溃或出现错误结果,所以需要我们去处理这些异常,让程序能更稳健…

MySQL基础 数据库表的增删改

Mysql 数加科技整理 一、原理定义概念 定义数据库(Database)是按照数据结构来组织、存储和管理数据的建立在计算机存储设备上的仓库。 数据库是长期储存在计算机内、有组织的、可共享的数据集合。分类: ​ 非结构化数据: ​ 数据相对来讲没有固定的特点,这种数据非常不便于…

加入我们|申请成为亚马逊云科技 Community Builder,共建云端社区!

亚马逊云科技 Community Builder 项目为开发者社区中的技术爱好者和新兴思想领袖提供技术资源、学习和交流机会,帮助开发者探索、分享技术相关知识,并与亚马逊云科技产品团队、技术专家和更多开发者社区成员建立紧密联系。亚马逊云科技开发者社区为开发者们提供全球的开发技术…

[ARC070E] NarrowRectangles

前言 模拟赛 \(\rm{T4}\) , 不会比较正常, 仅仅只是记录做法 然后就是还有每日一练 思路 首先是朴素的 \(\rm{dp}\) 令 \(f_{i, j}\) 表示考虑到第 \(i\) 行, 其中这一行的左端点位置为 \(j\) 的最优花费 容易写出转移 \[f_{i, j} \gets \min_{k \in [j - len_{i - 1}, j + len…

PDF Automation文档页面自动化工具

PDF Automation是我用VB6开发的一个PDF文档页面自动化工具。电脑必须安装了Adobe Acrobat才能使用该工具。软件的主要功能包括:文档的拆分 文档的合并 页面的删除 页面的移动 页面的插入等。 软件界面正中央的区域是文档列表,也就是多个PDF文档,最右侧是页面列表,显示当前所…