follower
先讲第一个状态follower的处理
所有的server重启后第一个状态都是follower,如果在election timeout时间内,既没有收到leader的heartbeat,也没有收到RequestVote请求,那么开启选举过程,此时状态将转换为candidate
candidate
接着开始第二个状态candidate的处理:
第一步,新增本地任期和投票
第二步,重置 election timer 并开始广播
第三步等待结果
1)他自己赢得了选举;
2)收到AppendEntries得知另外一个服务器确立他为Leader,转变为follower
- 一个周期时间过去但是没有任何人赢得选举,开始新的选举
leader
如果此时赢得了选举,则进入第3个状态leader的处理:目前leader只实现了一个功能,周期性的发送心跳,功能非常简单,此处不再贴代码了。
rpc
剩下就是两个rpc的发送和接收处理了,其中需要特别注意的点如下:
所有rpc处理中:如果收到的请求或者响应中,包含的term大于当前的currentTerm,设置currentTerm=term,然后变为follower
所有rpc处理中:判断任期是否小于currentTerm,小于的都丢弃
在完成第一个测试的过程中:AppendEnties只需要处理心跳请求即可
第一阶段 Prepare 阶段,广播自己的编号到集群中的其他Server,收到提议的Server 如果发现这个提议编号比自己记录的minProposal 大,则将minProposal的值修改为该值。可以认为,接受提议的Server
都会尝试修改自己的minProposal。
第二阶段 Accept 阶段:
1.(发起端)如果第一阶段有返回 (AcceptedProposal,AcceptedValue),则选择返回中 AcceptedProposal 最大的AcceptedValue 作为此次Accept 请求的value。否则,使用提议者自己的value。
2.(接收端)服务器接收到Accept请求后,会将发起者的编号和自己的minProposal进行对比。如果大于等于自己的编号,则认为此次请求有效,进行更改。否则,认为此次请求是一个古老的请求,不予修改。并返回对应的minPorposal给发起方。
3.(发起端)发起端收到大多数回复后,如果有任何服务器拒绝 Accept (result > 提议编号),则递增编号,重新发起提议。否则,认为此次提议通过。
这里稍微总结一下 :
其实,对于除发起提议者以外的其他服务器来说,他们并不知道一个值是否最终被确认。尽管某个值可能被自己Accept,但是是否被大多数Server Accept它是不知道的。只有发起提议方根据返回的结果能确认这个提议是被通过的。简而言之,一个除发起方以外的服务器,如果想知道哪个提议被选中,必须自己亲自执行一遍Paxos协议 。
网友评论