通俗易懂!从中国男篮输球谈一谈分布式Gossip协议
分布式协议,是分布式中的难点,很多程序员都难以理解什么是协议?作用是什么?为何要如此实现?以及其中的算法精髓,今天我们通过中国男篮的例子,来讲一讲,分布式协议中的Gossip协议。
首先,我们应该理解分布式协议是做什么的,分布式,意味着多机部署,那么,不同机器之间是如何进行通信的呢?我们将不同机器之间的交流称之为协议,主要用来分布式环境下不同机器之间的通信,保证集群下不同机器间的数据交流与数据一致性
Gossip协议,是一个比较简单的分布式协议,它的小名又叫留言传播,被广泛应用到各个系统当中,Redis官方多机部署方案中,亲儿子RedisCluster用的正是Gossip协议。
基本原理
在Gossip协议中,是怎么运作的呢?简单来说,就是当一个人得到新的消息之后(可以是发现新节点,也可以是发现某个机器挂了),就会随机向他的周边节点传播,最后整个集群都知道这个消息。好比中国男篮输球了,易建联空砍24分,大家开始纷纷对周边的人说,可以发朋友圈,可以大声咆哮,可以在群里抱怨,最后大家都知道了最终结果,这便是Gossip协议的基本原理。为了节约资源,一般Gossip的实现方法都是限定每隔单位时间,像其他人进行发送,好比你不会一下子对所有朋友都说中国男篮的消息,那样子对服务的压力就太大了,不能因为机器间的同步占用大量资源而无法保证机器正常服务。
最终一致性
在Gossip协议中,每个机器都能传播自己的最新消息,那么如何保证数据是正确的呢?答案是不能保证数据是每时每刻所有机器上面的数据都是对的,但是可以保证数据最终是对的,也就是最终一致性。好比中国男篮对波兰的比赛进行到第四节最后40秒,中国队领先3分,这个时候,有点节点就开始对外播报“稳了稳了,中国男篮挺进第二轮”。这条消息开始在集群里面进行传播,很快就有机器信以为真了。很快,又要机器发现了,周琦进攻犯规,并且连续失误,双方分差只差1分,悬了!并且将这条消息进行广播。这个时候之前收到中国队赢了的消息节点,慢慢的收到了这条消息,发现冲突了!怎么办!会进行版本号对比,在中国男篮的例子中,也就是对比比赛的时间,发现新的消息更新,把自己的状态更新为中国队悬了。同理,到了加时赛最后,有的机器开始开始广播“赵睿拼尽全力5犯,易建联错失绝杀”,整个集群都知道了,中国男篮输了,并且随着消息的扩散,最终整个集群都保持这个状态,这个时候有可能有的节点才刚刚收到“稳了稳了”的消息,但是通过版本号对比,抛弃了这个状态,从而保证集群最终状态的一致。
节点发现
Gossip协议是一个去中心化的协议,也就是说没有中心结点,如何理解这一点呢?那么当集群扩容的时候,其他机器是如何知道的呢?在Gossip协议中,每个机器都会维护者一个其他机器列表,就好比每个人心中,自己的好友,有哪些人也看球。到了昨天晚上,有人发了中国男篮输球了,周琦大魔王。这个时候,你会惊讶,原来这个人也看球,并且把他加到了看球列表中,下次有空的时候,你就会跟其他朋友说,某某某也是看球的,很快整个集群就知道了,新加入一台新的机器了。
节点移除
Gossip协议的一大重大作用,便是移除不可用的节点,我们来谈一谈RedisCluster中,Gossip协议是如何移除不可用节点的。当实例A发现实例B不可用的时候,就会对集群传播一条消息,说实例B不可用,当其他实例接收到这个消息时候,会对实例B进行探测,如果实例C发现实例B也不可用,也会跟着发出实例B不可用的信息。当集群里面,发出实例B不可用的数量超过一半的时候(多数派原则),就会发出一条新的消息,实例B确实不可用,进行主备切换!强制集群其他机器,断开实例B的连接,使用或者投票出实例B的Slave实例。
总结
Gossip协议,扩展性强,可以随便增减机器,容错率高,没有中心节点,又能保证最终一致性,关键是实现起来也是较为简单,所以被广泛的应用。
rel: http://dy.163.com/v2/article/detail/EO4VU41405318EGN.html