Raft算法

Posted by Liao on 2023-02-24

前言

如果有多个机器(集群),则需要保证每个机器数据的一致性,这时候则需要分布式共识算法。Raft是实现分布式共识算法的协议,除了Raft,还有Paxos、ZAB、Gossip等。

Leader election

每个节点有三个状态,分别是LeaderFollowerCandidate

  • 一开始的时候,所有节点都处于Follower的状态。每个结点都有一个Election Timeout(随机在150ms-300ms,可以在config中设置),如果有一个结点超时没有从Leader中获得消息,它们则会变为Candidate

  • Candidate会向其它结点请求投票数,在任期之内没有投票过的Follower可以投票(避免重复投票)。

  • 若获得超过半的投票数(保证了leader的唯一性),则该Candidate会变成Leader,其它的follower的会重置计时器(不着急成为candidate)

    • 若获得平票,则等待timeout并重新发起选举(因为timeout是随机数,因此平票几率少)
  • Leader会周期地发送Heartbeat Timeout给Followers,以重置timer,使其不会因为超时而变为Candidate(因为选举是一个耗时的操作,如果leader存活的话,则不用频繁更换leader)。Followers会返回AppendEntries的消息给Leader。

Log replication

如果集群中一个机器挂了,通过把日志复制到(广播)到其它服务器,其它的服务器都会有共识/majority,可以用于恢复日志(容错性)

  • 当client给leader发送操作请求,leader都会将请求记录在该结点的日志行中,此时的数据是uncommitted状态(不会改变原来的值,机器挂掉/网络故障了该操作也不会被保存下来)
    • Client对系统的操作(读、写)都要通过leader同意,若client把请求发送给follower,follower同样要把请求转发给leader
  • 然后leader结点会通过next hearbeat把该请求replicates到别的follower结点中。followers发送AppendEntries请求,将数据操作写到本地日志中(uncommitted状态),ok的话,会返回一个投票。
  • 若超过半数的Followers知道了操作变更,则Leader会把操作写入(AppendEntries),变为commited状态(已持久化状态),并通知其它followers将本地日志中uncommitted的日志改committed,并更新数据。返回相应给client
  • 此时,整个集群的数据是一致的(consensus)

参考