现在的位置: 首页 > 综合 > 正文

redis cluster源码研究–failover

2018年03月30日 ⁄ 综合 ⁄ 共 2832字 ⁄ 字号 评论关闭

    failover是redis cluster的容错机制,是redis cluster最核心功能之一;它允许在某些节点失效情况下,集群还能正常提供服务。

    redis cluster采用主从架构,任何时候只有主节点提供服务,从节点进行热备份,故其容错机制是主从切换机制,即主节点失效后,选取一个从节点作为新的主节点。在实现上也复用了旧版本的主从同步机制。

    从纵向看,redis cluster是一层架构,节点分为主节点和从节点。从节点挂掉或失效,不需要进行failover,redis cluster能正常提供服务;主节点挂掉或失效需要进行failover。另外,redis cluster还支持manual failover,即人工进行failover,将从节点变为主节点,即使主节点还活着。下面将介绍这两种类型的failover。

一、主节点失效产生的failover

1、(主)节点失效检测 

     一般地,集群中的节点会向其他节点发送PING数据包,同时也总是应答(accept)来自集群连接端口的连接请求,并对接收到的PING数据包进行回复。 

当一个节点向另一个节点发PING命令,但是目标节点未能在给定的时限(node timeout)内回复时,那么发送命令的节点会将目标节点标记为PFAIL(possible failure)。 

由于节点间的交互总是伴随着信息传播的功能,此时每次当节点对其他节点发送 PING 命令的时候,就会告知目标节点此时集群中已经被标记为PFAIL或者FAIL标记的节点。 

相应的,当节点接收到其他节点发来的信息时, 它会记下那些被其他节点标记为失效的节点。 这称为失效报告(failure report)。 

如果节点已经将某个节点标记为PFAIL,并且根据节点所收到的失效报告显式,集群中的大部分其他主节点(n/2+1)也认为那个节点进入了失效状态,那么节点会将那个PFAIL节点的状态标记为FAIL。 

      一旦某个节点被标记为FAIL,关于这个节点已失效的信息就会被广播到整个集群,所有接收到这条信息的节点都会将失效节点标记为FAIL。

2、选举主节点

     一旦某个主节点进入 FAIL 状态, 集群变为FAIL状态,同时会触发failover。failover的目的是从从节点中选举出新的主节点,使得集群恢复正常继续提供服务。

    整个主节点选举的过程可分为申请、授权、升级、同步四个阶段: 

(1)申请 

    新的主节点由原已失效的主节点属下的所有从节点中自行选举产生,从节点的选举遵循以下条件: 

a、这个节点是已下线主节点的从节点; 

b、已下线主节点负责处理的哈希槽数量非空;

c、主从节点之间的复制连接的断线时长有限,不超过 ( (node-timeout * slave-validity-factor) + repl-ping-slave-period )。

    如果一个从节点满足了以上的所有条件,那么这个从节点将向集群中的其他主节点发送授权请求,询问它们是否允许自己升级为新的主节点。

   从节点发送授权请求的时机会根据各从节点与主节点的数据偏差来进行排序,让偏差小的从节点优先发起授权请求。

(2)授权 

   其他主节点会遵信以下三点标准来进行判断: 

a、 发送授权请求的是从节点,而且它所属的主节点处于FAIL状态 ;

b、 从节点的currentEpoch〉自身的currentEpoch,从节点的configEpoch>=自身保存的该从节点的configEpoch;

c、 这个从节点处于正常的运行状态,没有被标记为FAIL或PFAIL状态;

   如果发送授权请求的从节点满足以上标准,那么主节点将同意从节点的升级要求,向从节点返回CLUSTERMSG_TYPE_FAILOVER_AUTH_ACK授权。

(3)升级 

    一旦某个从节点在给定的时限内得到大部分主节点(n/2+1)的授权,它就会接管所有由已下线主节点负责处理的哈希槽,并主动向其他节点发送一个PONG数据包,包含以下内容: 

a、 告知其他节点自己现在是主节点了 

b、 告知其他节点自己是一个ROMOTED SLAVE,即已升级的从节点;

c、告知其他节点都根据自己新的节点属性信息对配置进行相应的更新 

(4)同步   

    其他节点在接收到ROMOTED SLAVE的告知后,会根据新的主节点对配置进行相应的更新。特别地,其他从节点会将新的主节点设为自己的主节点,从而与新的主节

点进行数据同步。

    至此,failover结束,集群恢复正常状态。

    此时,如果原主节点恢复正常,但由于其的configEpoch小于其他节点保存的configEpoch(failover了产生较大的configEpoch),故其配置会被更新为最新配置,并将自己设新主节点的从节点。

    另外,在failover过程中,如果原主节点恢复正常,failover中止,不会产生新的主节点。

二、Manual Failover

    Manual Failover是一种运维功能,允许手动设置从节点为新的主节点,即使主节点还活着。

    Manual Failover与上面介绍的Failover流程大都相同,除了下面两点不同:

   (1)触发机制不同,Manual Failover是通过客户端发送cluster failover触发,而且发送对象只能是从节点;

   (2)申请条件不同,Manual Failover不需要主节点失效,failover有效时长固定为5秒,而且只有收到命令的从节点才会发起申请。

     另外,Manual Failover分force和非force,区别在于:非force需要等从节点完全同步完主节点的数据后才进行failover,保证不丢失数据,在这过程中,原主节点停止写操作;而force不进行进行数据完整同步,直接进行failover。

    

三、集群状态检测

     集群有OK和FAIL两种状态,可以通过CLUSTER INFO命令查看。当集群发生配置变化时, 集群中的每个节点都会对它所知道的节点进行扫描,只要集群中至少有一个哈希槽不可用(即负责该哈希槽的主节点失效),集群就会进入FAIL状态,停止处理任何命令。 

    另外,当大部分主节点都进入PFAIL状态时,集群也会进入FAIL状态。这是因为要将一个节点从PFAIL状态改变为FAIL状态,必须要有大部分主节点(n/2+1)认可,当集群中的大部分主节点都进入PFAIL时,单凭少数节点是没有办法将一个节点标记为FAIL状态的。 然而集群中的大部分主节点(n/2+1)进入了下线状态,让集群变为FAIL,是为了防止少数存着主节点继续处理用户请求,这解决了出现网络分区时,一个可能被两个主节点负责的哈希槽,同时被用户进行读写操作(通过禁掉其中少数派读写操作,证保只有一个读写操作),造成数据丢失数据问题。

说明:上面n/2+1的n是指集群里有负责哈希槽的主节点个数。    

抱歉!评论已关闭.