分布式一致性协议之Raft

2020-03-11 16:45:08 浏览数 (1)

Raft-很容易理解的分布式一致性算法

单节点场景

你可以想象下我们的一个节点作为一个保存单一值的数据库服务,我们有一个client可以向server发送一个值。client与server的关系如下图:

如果client向server发送一个值为8,那么它们的关系将变成下图:

可以看到只有一个节点的时候就很容易达到协议共识。

多节点

有了上面的示例,我们不禁要问,当我们拥有多个节点时怎么来达成节点间的共识呢?

客户端的值8该怎么在节点a、b、c之间达成一致呢,这就是分布式共识的问题。

Raft

Raft就是分布式共识协议的一种实现。我们来看一看它是如何工作的。

首先,节点有三种状态:

  1. Follower(跟随节点)
  2. Candidate(候选节点)
  3. Leader(领导节点)

下文中的Term代表的是任期

所有的节点在最开始的时候都是follower状态:

如果followers没有接收到leader的心跳请求(这里有一个超时时间,超过这个时间就认为没有接收到)然后它们就会变成candidate节点,如下图中的a节点:

然后candidate节点(图中a节点)开始请求其他节点投票。节点b和c将会回复给出他们的投票。

如果这时候candidate节点得到了大多数节点的投票,它就会成为leader节点。这个过程就被称为选主。所有的系统变化都需要经过leader节点。

每个更改都作为一个条目添加到节点的日志中。此日志项当前未提交,因此不会更新节点的值。

要提交条目,节点首先需要将其复制到Follower节点中。

然后领导者等待,直到大多数节点都写了该条目。

现在,该条目已提交到Leader节点上,并且节点状态为“ 5”。

然后Leader通知Follower该条目已提交。

现在,集群已就系统状态达成共识。此过程称为日志复制。

选举

在Raft中,有两个超时设置可控制选举。

首先是选举超时。选举超时是指追随者成为候选人之前所等待的时间。选举超时被随机分配在150毫秒至300毫秒之间。选举超时后,关注者成为候选人并开始新的选举任期:

图中Node C超时后为自己投票,并向其他节点发送请求投票消息。

如果接收节点在这个选举周期内还没有投票,那么它将投票给候选人:

在投票的同时会对节点重置其选举超时。

一旦候选人获得多数票,便成为Leader:

Leader开始向其Follower发送“ 添加条目”消息。

这些消息以心跳超时指定的时间间隔发送。Follower然后响应每个追加条目消息。

此选举任期将持续到Follower停止接收心跳并成为候选人为止:

让我们停止Leader,观察选举连任:

假设图中节点B先达到选举超时率先变成Candidate节点,它将成为任期2的负责人:

节点B向节点A和节点C请求投票,但是只有节点A返回了投票响应:

成为Leader的另一个条件是要获得多数票,这样可以确保每个任期只能选出一位Leader。如果两个节点同时成为候选节点,则可能会发生拆分表决。

让我们看一个分割投票的例子:

如果节点A和节点C都开始以相同的任期进行选举:

每个都先到达一个Follower节点:

现在,每位候选人都有2票,并且在这个任期中将无法获得更多选票:

这时Node节点将会等待一个新的超时时间重新进行投票:

节点C在第5届中获得了多数选票,因此成为领导者:

日志复制

当选出一位Leader后,我们需要将系统的所有更改复制到所有节点:

通过使用与心跳相同的“ 添加条目”消息来完成此操作。让我们逐步完成该过程。

首先,客户将更改发送给Leader:

更改将添加到Leader的日志中:

然后将更改在下一个心跳发送给Follower,一旦大多数Follower认可,便提交该条目:

然后将响应发送给客户端:

现在,让我们发送一条命令,将值增加“2”:

我们的系统值现在更新为“7”:

网络分区

Raft甚至可以在面对网络分区时保持一致:

对上图中一个集群,让我们添加一个分区以将A&B与C,D&E分开:

由于我们的分区,我们现在有两位Leader。让我们添加另一个客户端,并尝试更新两个领导者。

一个客户端将尝试将节点B的值设置为“ 3”

节点B无法复制为多数,因此其日志条目保持未提交状态。

另一个客户端将尝试将节点E的值设置为“ 8”

这将成功,因为它可以复制到大多数

现在让我们修复网络分区

节点B将看到较高的选举任期并退出Leader角色。节点A和B都将回滚其未提交的条目并匹配新领导者的日志。

现在,我们的日志在整个集群中是一致的。

参考

文章译自:http://thesecretlivesofdata.com/raft/

另外,网络上有一张比较经典的图片描述本文的:

图片来自:https://www.codedump.info/post/20180921-raft/

0 人点赞