【Zookeeper】-选举机制
前言
最近在学习zookeeper 这块内容,将自己理解到的内容记录一下,希望对您有所帮助!
正文
zookeeper 集群中的三种服务器角色 |
通常在分布式系统中,构成一个集群的每一台机器都有自己的角色,最典型的集群模式就是Master/Salve(主备模式),但是在Zookeeper中,引入了Leader、Follower、Observer 三种角色。
- Leader
Leader服务器是Zookeeper 集群工作的核心,是整个集群的管理者,Leader服务器为客户端提供读和写服务,它是事务请求的唯一调度和处理者,保证集群事务处理的顺序性;它也是集群内部各服务器的调度者。 - Follower
Follower 是集群的跟随者,处理客户端非事务性请求(读取数据),转发事务请求给leader服务器;参与事务请求Proposal的投票;参与Leader选举投票。 - Observer
观察者角色,观察Zookeeper集群的最新状态变化并将这些状态同步过来,对于非事务请求可以进行独立处理,对于事务请求,将会转发给Leader服务器进行处理,他们不参与选举和投票,仅仅接受选举和投票的结果。
Observer 的目的是为了扩展系统,在不影响写性能的情况下提高读取速度。
Zookeeper 节点的四种状态 |
- Looking
集群中所有机器都处于一种试图选举出一个Leader的状态, 寻找Leader 状态,当Server处于该状态时,此Server会认为当前集群中没有Leader,需要进入Leader选举状态。 - Following
跟随者状态,表明该服务器角色为Follower。 Leading
领导者状态,表明该服务器角色为Leader。Observing
观察者状态,表明当前服务器角色是Observer。
为什么需要Leader选举? |
选举出一个Leader,主要是为了保持分布式数据的一致性,每个节点的存储的数据保持同步。
Leader选举机制概述 |
Leader 选举可以说是集群和单机模式启动Zookeeper 的最大的不同点。Zo’okeeper 会根据zoo.cfg 中的配置,创建相应的Leader选举算法实现。在Zookeeper中,默认提供了三种Leader选举算法的实现:LeaderElection、AuthFastLeaderElection和FastLeaderElection,从3.4.0 版本开始,zookeeper 废弃了前两种Leader选举计算法,只支持FastLeaderElection选举算法了。
什么时候进入Leader选举? |
- 服务器初始化启动
- 服务器运行期间无法和Leader 保持连接
Leader选举流程 |
概念了解
这里以3台机器组成的服务器半”的要求。
- 过半机器数(Quorum) :指大于集群机器数量的一半,即大于或等于(n/2+1),对于这里的由3(n=3)台机器构成的集群,大于等于2台即为达到“过半”的要求。
- ZXID : 是指一个事务ID,用来唯一标识一次服务器状态的变更。
- myid : 服务器ID(SID),用来唯一标识一台Zookeeper集群中的机器,每台机器不能重复。olve/70
模式1:服务器初始化时的Leader选举
在服务器集群初始化阶段,当有一台服务器(假设这台机器的myid 为1,因此称其为Server1)启动的时候,它是无法完成Leader选举的。当第二台机器(同样,假设这台服务器的myid为2,称其为server2)也启动后,此时这两台已经能够互相通信,每台一个Leader,于是便进入了Leader选举流程。
1、每个Server会发出一个投票
由于是初始情况,因此对于Server1和Server2来说,都会将自己作为Leader服务器来进行投票,每次投票包含的最基本的元素包括:所推举的服务器的myid 和ZXID ,我们以(myid,ZXID)的形式来表示。因为是初始化阶段,所以无论是Server1还是Server2 ,都会投给自己,即Server1的投票为(1,0),Server2的投票为(2,0),然后各自将这个投票发给集群中其他所有机器。
2、接收来自各个服务器的投票
每个服务器都会接收来自其他服务器的投票。集群中的每个服务器在接收到投票后,首先会判断该投票的有效性,包括检查是否是本轮投票,是否来自LOOKING 状态的服务器。
3、处理投票
在接收到来自其他服务器的投票后,针对每一个投票,服务器都需要将别人的投票和自己的投票进行PK,PK的规则如下。
- 优先检查ZXID。ZXID 比较大的服务器优先作为Leader。
- 如果ZXID相同的话,那么就比较myid。myid比较大的服务器作为Leader 服务器。
根据这样的PK 规则,我们来看下Server1和Server2实际是如何进行投票处理的:对于Server1来说,它自己的投票是(1,0),而接收到的投票为(2,0)。首先会对比两者的ZXID,因为都是0,所以无法决定谁是Leader,接下来会对比两者的myid,很显然,Sever1发现接收到的投票中的myid为2,大于自己,于是就会将自己的投票更新为(2,0),然后重新将投票发出去;而对于Server2来说,不需要更新自己的投票信息,只是再一次向集群中所有的机器发出上一次投票信息即可。
4、统计投票
每次投票后,服务器都会统计所有投票,判断是否已经有过半的机器接收到相同的投票信息。对于Server1 和Server2服务器来说,都统计出已经有两台机器接收了(2,0)这个投票信息。当Server1和Server2 都收到相同的投票信息(2,0)的时候,即认为已经选出了Leader。
5、改变服务器状态
一旦确定了Leader,每个服务器就会更新自己的状态:如果是Follower ,那么就变更为FOLLOWING ,如果是Leader,那么就变更为LEADING。
模式2: 服务器运行时的Leader选举
在Zookeeper 集群正常运行过程中,一旦选出一个Leader,那么所有服务器的集群角色一般不会再发生变化,也就是说,Leader服务器将一直作为集群的Leader,即使集群中有非Leader 机器挂了或者有新机器加入集群也不会影响Leader。但是一旦Leader所在的机器挂了,那么整个集群将暂时无法对外服务,而是进入新一轮的Leader选举。服务器运行期间的Leader选举和启动时期的Leader选举基本过程是一致的。
假设当前运行的ZooKeeper集群由3台机器组成,分别是Server1、Server2、Server3 ,当前的Leader 是Server2。假设再某一个瞬间,Leader挂了,这个时候就开始了Leader选举。
1、变更状态
当Leader挂了之后,剩下的非Observer 服务器都会将自己的服务器状态变更为LOOKING,然后开始进入Leader选举流程。
2、每个Server会发出一个投票
在这个过程中,需要生成投票信息(myid,ZXID)。因为是运行期间,因此每个服务器上的ZXID可能不同,我们假定Server1的ZXID为123,而Server3的ZXID为122。在第一轮投票中,Server1和Server3都会投自己,即分别产生投票(1,123)和(3,122),然后各自将这个投票发给集群中所有机器。
3、接收来自各个服务器的投票
4、处理投票
对于投票的处理,和上面提到的服务器启动期间的处理规则是一致的。这个例子中,由于Server1的ZXID为123,Server3的ZXID 为122,那么,Server1会成为Leader。
5、统计投票
6、改变服务器状态
选举算法核心:变更投票 |
假设Zookeeper 集群由5台服务器组成,SID 分别为1、2、3、4和5,ZXID 分别为9、9、9、8和8 ,并且此时SID 为2的机器是Leader服务器,某一时刻,1和2所在的机器出现故障,因此集群开始Leader选举。
集群中每台机器发出自己的投票后,也会收到来自集群种其他机器的投票。下面是处理投票:
Leader选举小结 |
简单地说,通常哪台服务器上的数据越新,那么越有可能成为Leader,因为数据越新,它的ZXID 越大,也就越能保证数据的恢复。如果集群种有几个服务器具有相同的ZXID,那么SID(myId)较大的那台服务器成为Leader。
总结
Leader 选举机制暂时说到这里,感谢您的耐心阅读!