当前位置: 首页 > news >正文

实用指南:ZooKeeper 的选举算法

1. 背景介绍

Apache ZooKeeper 是分布式系统中常用的协调服务框架,提供配置管理、命名服务、分布式锁和集群管理等功能。
在一个 ZooKeeper 集群中,有三类角色:

  • Leader:负责事务请求的处理和集群内数据同步。

  • Follower:处理非事务请求,参与投票选举,接受 Leader 的同步。

  • Observer:不参与投票,仅作为读请求的分流节点。

ZooKeeper 的核心目标是保证数据一致性。因此,当 Leader 节点宕机或网络分区时,ZooKeeper 必须通过选举算法快速选出新的 Leader,保证系统继续正常运行。

2. ZooKeeper 的选举触发条件

选举算法会在以下场景触发:

  1. 集群启动时,没有 Leader,需要选举。

  2. Leader 节点宕机或失联,需重新选举。

  3. 节点间网络分区,部分节点失去对 Leader 的感知。


3. 选举算法的演进

ZooKeeper 核心启用三种选举算法:

3.1 基于 UDP 的 LeaderElection(早期版本)

  • 使用 UDP 广播进行投票交换。

  • 存在可靠性问题,容易丢包,已经逐步淘汰。

3.2 基于 TCP 的 LeaderElection

  • 改用 TCP 保证消息可靠传输。

  • 选举效率比 UDP 稳定,但实现较艰难。

3.3 FastLeaderElection(目前主流)

  • Hadoop/ZooKeeper 3.4 之后的默认算法。

  • 基于 TCP 进行投票,支持epoch(逻辑时钟)ZXID(事务 ID) 的比较。

  • 高效、健壮,能够迅速收敛到一个新的 Leader。


4. FastLeaderElection 算法原理

ZooKeeper 的选举过程依赖三个关键信息:

  1. myid:节点 ID,每个节点唯一。

  2. ZXID:事务日志 ID,反映节点材料最新程度。

  3. epoch:逻辑时钟,区分不同轮次的选举。

核心投票规则:

  • 优先比较 epoch(逻辑时钟),epoch 越大越新。

  • 如果 epoch 相同,比较ZXID,数据更新的节点更优。

  • 若是 ZXID 也相同,比较myid,ID 较大的节点胜出。

选举步骤:

  1. 所有节点进入LOOKING状态,发起投票。

  2. 每个节点先投自己一票,广播给集群。

  3. 收到其他投票后,比较 epoch/ZXID/myid,更新自己的投票。

  4. 当某个候选人获得超过半数节点的帮助时,该候选人成为新的 Leader。

  5. 其他节点更新为FOLLOWING/OBSERVING状态,达成选举。


5. 举例说明

假设一个 ZooKeeper 集群中有 5 个节点:

  • 节点 1:ZXID=5

  • 节点 2:ZXID=8

  • 节点 3:ZXID=6

  • 节点 4:ZXID=8

  • 节点 5:ZXID=7

选举过程:

  1. 初始时,所有节点都投自己。

  2. 节点间交换投票后,发现 ZXID 最大的是 8(节点 2 和 4)。

  3. ZXID 相同的情况下,比较 myid,节点 4 的 ID 大于节点 2。

  4. 节点 4 获得超过半数的支持,成为新的 Leader。


6. ZooKeeper 选举算法的优缺点

优点:

  • 快速收敛:利用过半原则,保证最终一致性。

  • 高可靠性:基于 TCP 通信,减少丢包问题。

  • 数据安全:优先选择数据最新的节点作为 Leader。

缺点:

  • 在大规模集群中,选举过程可能带来额外的网络开销。

  • 网络分区时可能导致脑裂,需要依赖过半原则避免。


7. 总结

保证集群高可用性的核心机制。就是ZooKeeper 的选举算法

  • 早期 LeaderElection:基于 UDP,不可靠。

  • TCP LeaderElection:基于 TCP,改进可靠性。

  • FastLeaderElection:目前主流,基于 epoch + ZXID + myid 的比较规则,高效可靠。

一句话总结:

ZooKeeper 通过 FastLeaderElection 算法,确保在 Leader 故障时能快速选出新的 Leader,从而保证集群的一致性和高可用性。

http://www.hskmm.com/?act=detail&tid=7346

相关文章:

  • JAVA获取keytab的Principal
  • 基于霍夫变换的MATLAB虹膜检测与分割实现
  • Linux时间同步---NTP时间同步方案
  • java预习
  • B/S体系结构风格
  • The 2024 CCPC Online Contest 7/12 L/B/K/D/J/E/C
  • 在joule里面使用agent 功能
  • Feign动态URL配置
  • 自动化部署工具 Jenkins 的安装与配置
  • pip 搭建源
  • qoj10093 Jump the Frog
  • new 和make
  • Ceres 常用 LossFunction 对比
  • python函数
  • git使用
  • 测试开发全日制学徒班火热报名中|跟着名企大咖做真实项目,结业即上岗
  • 墨刀是否能替代Axure?从产品经理三大画图能力深度分析
  • AI 自动化智能体训练营
  • 微信商户绑定微信公众号、小程序
  • 唯创知音AI语音交互芯片与模组介绍
  • k3s 高可用集群部署(内置 etcd + VIP + keepalived)
  • 问HashMap底层原理?
  • 用 Go 重写 adbkit:原理、架构与搭建实践
  • C语言环境搭建之Linux子系统使用vscode连接子系统
  • 移远AT指令笔记
  • C++ 智能指针
  • 数据类型
  • iphone运行windows系统
  • NVR接入录像回放平台EasyCVR视频融合平台语音对讲配置指南
  • Ubuntu filebrowser网盘工具安装