锐单电子商城 , 一站式电子元器件采购平台!
  • 电话:400-990-0325

Redis 集群中的纪元(epoch)

时间:2022-10-18 23:30:00 二极管ppm3fd201e0

文章转载方便整理归纳,源文地址:https://zhuanlan.zhihu.com/p/44658603

Redis Cluster 类似使用 Raft 算法 term(任期)的概念叫 epoch(时代),用于为事件添加版本号。Redis 集群中的时代主要有两种:currentEpochconfigEpoch

时间可以通过cluster nodes命令或cluster info命令查看。
cluster nodes返回的结果connected关键字前面的数字是一个例子epoch

[root@redis-7-221 logs]# redis-cli -p 9001 cluster nodes 37dc860d2cc031c7d0a052bb34c07ad1625cbe8f 10.4.7.222:9011 slave 335a0cb8d9d82a764a19bf71da6379b73c703e95 0 1648436204016 7 connected 5f201e00106a512ab3a3d73455ee1269b367b204 10.4.7.222:9002 master - 0 1648436205026 4 connected 4097-8192 577e5ea9c7f56c3767cfcfa23905742d97448b02 10.4.7.221:9013 master - 0 1648436206542 8 connected 8193-12288 097271ce6ad0d7c5b4e5b80a645058bd2bb0099f 10.4.7.221:9004 master - 0 1648436207048 6 connected 12289-16383 dcf4c5f00f922e67094ebd0bf0cfe61701c0c3fe 10.4.7.222:9014 slave 097271ce6ad0d7c5b4e5b80a645058bd2bb0099f 0 1648436208069 6 connected 335a0cb8d9d82a764a19bf71da6379b73c703e95 10.4.7.221:9001 myself,master - 0 0 1 connected 0-4096 

cluster info命令返回的 cluster_current_epoch最大的集群epoch纪元值,cluster_my_epoch以实例为例。

[root@redis-7-221 logs]# redis-cli -p 9001 cluster info cluster_state:ok cluster_slots_assigned:16384 cluster_slots_ok:16384 cluster_slots_pfail:0 cluster_slots_fail:0 cluster_known_nodes:10 cluster_size:4 cluster_current_epoch:9 cluster_my_epoch:1 cluster_stats_messages_sent:233871 cluster_stats_messages_received:53172 

currentEpoch

这是一个与集群状态相关的概念,可以作为记录集群状态变化的增加版本号。每个集群节点将通过 server.cluster->currentEpoch 记录当前的 currentEpoch

无论是创建集群节点, master 还是 slave,都置 currentEpoch 为 0。当前节点接收到来自其他节点的包时,如果发送者的 currentEpoch(发送者将包含在消息头部。 currentEpoch)大于当前节点currentEpoch,然后将更新当前的节点 currentEpoch 为发送者的 currentEpoch。因此,集群中所有节点 currentEpoch 最终会达成一致,相当于对集群状态的认知。

currentEpoch 作用

currentEpoch 其功能是,当集群状态发生变化时,某个节点需要寻求其他节点的同意才能执行某些动作 currentEpoch 的值。目前 currentEpoch 只用于 slave 这与哨兵中的故障转移过程有关sentinel.current_epoch 功能完全一样。 slave A 找到它属于的 master 当离线时,将试图启动故障转移过程。首先是增加 currentEpoch 增加后的值 currentEpoch 是所有集群节点中最大的。slave A 向所有节点发起拉票请求,请求其他节点 master 投票给自己,让自己成为新的 master。收到包后,其他节点发现发送者 currentEpoch 比自己的 currentEpoch 大,会更新自己的 currentEpoch,在没有投票的情况下,投票 slave A,同意让它成为新的 master

configEpoch

这是一个与集群节点配置相关的概念,每个集群节点都有自己独特的 configepoch。所谓节点配置,其实是指节点负责的槽位信息。

每一个 master 将包发送到其他节点时,会附加到其他节点 configEpoch 信息,以及一份表示它负责的信息 slots 信息。而 slave 将包发送到其他节点时,包中 configEpoch 以及负责槽位的信息 masterconfigEpoch 和负责的 slot 信息。节点收到包后,会根据包中的要求 configEpoch 和负责的 slots 在相应的节点属性中记录信息。

configEpoch 作用

configEpoch 主要用于解决不同节点配置的冲突。例如,节点理解:A 宣称负责 slot 1,它向外发送的包包包含自己 configEpoch 和负责的 slots 信息。节点 C 收到 A 发包后发现自己目前没有记录 slot 1 负责节点(即 server.cluster->slots[1] 为 NULL),就会将 A 置为 slot 1 的负责节点(server.cluster->slots[1] = A),并记录节点 A 的 configEpoch。后来,节点 C 又收到了 B 它还声称对发送的包负责 slot 1,此时,如何判断 slot 1 谁负责?

这就是 configEpoch 该起作用了,C 在 B 发来的包里发现了它 configEpoch,要比 A 的大,说明 B 是更新配置。因此,它将是 slot 1 负责节点设置为 B(server.cluster->slots[1] = B)。在 slave 发起选举,获得足够的选票,成功当选,即 slave 试图取代已经离线的旧旧 master,成为新的 master 会增加自己的 configEpoch,使其成为当前所有集群节点 configEpoch 最大值。这样,应该 slave 成为 master 之后,将广播包发送到所有节点,强制其他节点更新 slots 对自己负责。

参考资料

  1. Redis Cluster Specification
  2. Redis cluster tutorial
  3. Redis系列九:redis集群高可用
  4. Redis源码解析:27集群(三)主从复制、故障转移

License

  1. 封面图片 Photo by**Andrew Haimerl**
  2. 遵守创作共享 CC BY-NC-SA 3.0协议
锐单商城拥有海量元器件数据手册IC替代型号,打造电子元器件IC百科大全!

相关文章