Redis.6.2 故障恢复
故障节点变为客观下线后,如果下线节点是持有槽的主节点则需要在它的从节
点中选出一个替换它,从而保证集群的高可用。下线主节点的所有从节点承担
故障恢复的义务,当从节点通过内部定时任务发现自身复制的主节点进入客观
下线时,将会触发故障恢复流程。
1.资格检查
每个从节点都要检查最后与主节点断线时间,判断是否有资格替换故障的主节
点。如果从节点与主节点断线时间超过 cluster-node-time*cluster-slavevalidity-factor,则当前从节点不具备故障转移资格。参数 cluster-slavevalidity-factor 用于从节点的有效因子,默认为 10。
2.准备选举时间
当从节点符合故障转移资格后,更新触发故障选举的时间,只有到达该时间后
才能执行后续流程。故障选举时间相关字段如下:
struct clusterState {
...
mstime_t failover_auth_time; /* 记录之前或者下次将要执行故障选举时间 */
int failover_auth_rank; /* 记录当前从节点排名 */
}
这里之所以采用延迟触发机制,主要是通过对多个从节点使用不同的延迟选举
时间来支持优先级问题。(具体伪代码另有文档)
3.发起选举
当从节点定时任务检测到达故障选举时间(failover_auth_time)到达后,发起选举流程如下:
(1) 更新配置纪元
配置纪元是一个只增不减的整数,每个主节点自身维护一个配置纪元
(clusterNode.configEpoch)标示当前主节点的版本,所有主节点的配
置纪元都不相等,从节点会复制主节点的配置纪元。
配置纪元的应用场景有:
·新节点加入。
·槽节点映射冲突检测。
·从节点投票选举冲突检测。
(2)广播选举消息
在集群内广播选举消息(FAILOVER_AUTH_REQUEST),并记录已发送
过消息的状态,保证该从节点在一个配置纪元内只能发起一次选举。消
息内容如同 ping 消息只是将 type 类型变为
FAILOVER_AUTH_REQUEST。
4.选举投票
只有持有槽的主节点才会处理故障选举消息
(FAILOVER_AUTH_REQUEST),因为每个持有槽的节点在一个配置纪
元内都有唯一的一张选票
投票过程其实是一个领导者选举的过程,如集群内有 N 个持有槽的主节点
代表有 N 张选票。由于在每个配置纪元内持有槽的主节点只能投票给一个从节点,因此只能有一个从节点获得 N/2+1 的选票,保证能够找出唯一的从节点。
例如集群内有 5 个持有槽的主节点,主节点 b 故障后还有 4 个,当其中一
个从节点收集到 3 张投票时代表获得了足够的选票可以进行替换主节点操作,故障主节点也算在投票数内,假设集群内节点规模是 3 主 3 从,其中有 2个主节点部署在一台机器上,当这台机器宕机时,由于从节点无法收集到
3/2+1 个主节点选票将导致故障转移失败。这个问题也适用于故障发现环节。
因此部署集群时所有主节点最少需要部署在 3 台物理机上才能避免单点问题。