Zookeeper 是由 Apache 提供的开源分布式协调服务,专为分布式应用程序提供可靠的协调和同步功能。它在保证数据一致性和高可用性方面扮演着至关重要的角色。
1. Zookeeper 的架构与工作原理
Zookeeper 采用 Leader-Follower 架构,集群通常由奇数个节点(服务器)组成,以确保在网络分区或节点故障时仍能实现一致性与可用性。核心机制是 ZAB 协议(Zookeeper Atomic Broadcast),一种崩溃恢复的原子广播协议,保证了在网络分区和崩溃时的最终一致性和持久性。
Zookeeper 的主要组件:
Leader 节点:唯一接受客户端的写请求,负责将更新操作广播给其他节点,维护系统数据的一致性。
Follower 节点:负责处理读取请求,并将写请求转发给 Leader 节点。它们在选举过程中参与投票,帮助选择新的 Leader。Observer 节点:用于扩展系统读取负载,不参与投票选举,适合在读取需求较高的场景中进行横向扩展。
数据模型:Zookeeper 的数据模型类似于 Unix 文件系统,采用层次化的树形结构,节点称为 Znode。每个 Znode 都可以存储数据和子节点,同时支持 临时节点(客户端会话结束时自动删除)和 持久节点(持久化存储)。
一致性保证:Zookeeper 保证了顺序一致性、原子性、单一系统映像、实时性和持久性。每个客户端视角中的 Zookeeper 状态是强一致的,即使在网络分区和故障恢复过程中,通过 ZAB 协议,Leader 将日志条目同步至多数 Follower 才能确认事务提交,确保一致性。
2. Zookeeper 的使用场景
1. Leader 选举:分布式系统中,协调多个节点选出一个领导者是关键操作。例如,Hadoop HDFS 使用 Zookeeper 进行 Namenode 的故障转移和选举,避免单点故障。选举机制基于创建临时顺序节点,最小编号的节点成为 Leader,其它节点监听其状态。
2. 分布式锁:在分布式系统中实现资源竞争的控制,Zookeeper 提供了强大的分布式锁功能。通过创建带有顺序编号的临时节点,客户端可实现锁的竞争与释放。当持有锁的客户端断开连接时,锁自动释放,确保无死锁或资源争用问题。
3. 配置管理:对于分布式系统,保持配置的一致性和动态更新是一项挑战。Zookeeper 允许开发者在 Znode 中存储配置信息,各个服务通过注册监听器监听配置变更,支持实时更新配置。例如,分布式数据流处理框架 Apache Storm 使用 Zookeeper 来协调任务拓扑和节点状态。
4. 服务注册与发现:Zookeeper 常作为服务注册中心,允许服务提供者注册其服务,消费者动态发现服务。在微服务架构中,Zookeeper 作为注册中心时,提供了服务实例信息的可靠同步和健康检查。例如,Dubbo 框架可以使用 Zookeeper 作为注册中心来实现服务发现和调用。
3. Zookeeper 的技术优势与挑战
优势:
强一致性:提供了强一致性保证,尤其适用于对状态同步有严格要求的分布式系统。高可用性和容错性:通过多数节点写入和崩溃恢复协议,保证在节点故障和网络分区时的数据可靠性和服务连续性。成熟稳定:Zookeeper 已被众多知名开源项目采用,如 Kafka、HBase、Solr 等,稳定性经过长时间验证。轻量级和高性能:Zookeeper 在分布式锁、元数据存储等场景中表现出色,尤其适合高并发读取场景。挑战:写性能瓶颈:由于写请求需要同步至多数节点,系统在写密集型应用中可能出现性能瓶颈。运维复杂性:Zookeeper 集群需要合理配置和监控,特别是在多数据中心部署时,网络延迟和分区可能增加维护复杂性。依赖网络环境:集群节点之间需要可靠的网络环境,以防止脑裂和性能降低。
4. Zookeeper 与其他技术框架的搭配
性能优化:确保 Zookeeper 部署在低延迟、高带宽的网络环境中,并将 Java 堆大小设置和垃圾回收参数调优,以提升响应时间。监控和告警:使用工具如 Prometheus 和 Grafana 进行 Zookeeper 的全面监控,包括延迟、会话数、请求速率和节点状态等,以便实现快速诊断和故障处理。通过深入理解其架构和优化策略,Zookeeper 能帮助开发者在分布式系统中实现高效的协调和一致性管理,是实现可靠分布式服务的基础性组件。
安装 Zookeeper 集群
1. 准备环境节点数:大规模 Zookeeper 集群通常会部署 3、5、7 等奇数个节点,以确保在出现节点宕机时仍能保持集群的可靠性。每个节点可以是不同的机器,也可以是同一台机器的不同虚拟机。操作系统:假设你在 CentOS 上安装。网络配置:集群中的每个节点必须可以相互访问(尤其是端口 2888 和 3888,分别用于集群内部通信和选举)。
2. 安装 Java 环境Zookeeper 需要 Java 环境。确保每个节点上都已安装 JDK 8 或更高版本:
sudo yum install java-1.8.0-openjdk
sudo yum install java-1.8.0-openjdk
3. 创建 Zookeeper 用户和目录在每台机器上创建一个 zookeeper 用户,并为 Zookeeper 设置数据存储目录:
sudo useradd zookeeper
sudo mkdir -p /opt/zookeeper
sudo chown zookeeper:zookeeper /opt/zookeeper
4. 下载 Zookeeper在每个节点上下载 Zookeeper 的二进制包,并解压到指定目录。假设在每个节点上都安装了相同版本的 Zookeeper。
cd /opt/zookeepersudo wget https://downloads.apache.org/zookeeper/stable/zookeeper-3.8.1.tar.gz
sudo tar -zxvf zookeeper-3.8.1.tar.gz
sudo ln -s zookeeper-3.8.1 zookeeper
sudo chown -R zookeeper:zookeeper /opt/zookeeper/zookeeper-3.8.1
5. 配置 Zookeeper 集群
5.1 配置文件:每个节点上的 zoo.cfg 配置文件都需要进行调整,以适应集群模式。可以从 zoo_sample.cfg 复制配置文件:
cd /opt/zookeeper/zookeeper/conf
sudo cp zoo_sample.cfg zoo.cfg
sudo chown zookeeper:zookeeper zoo.cfg
5.2 编辑 zoo.cfg 配置文件:你需要在每个节点的 zoo.cfg 中做如下配置:
dataDir=/var/lib/zookeeper
clientPort=2181
initLimit=5
syncLimit=2
tickTime=2000
dataDir=/var/lib/zookeeper
clientPort=2181
autopurge.snapRetainCount=3
autopurge.purgeInterval=1
其中,最重要的配置是 initLimit、syncLimit 和 server.X 配置。
5.3 配置集群节点:在每个节点的 zoo.cfg 文件中,添加集群节点的配置。假设集群有 3 个节点,节点 IP 地址为:Node 1: 192.168.1.101Node 2: 192.168.1.102Node 3: 192.168.1.103在每个节点的 zoo.cfg 文件中,添加如下内容:
server.1=192.168.1.101:2888:3888
server.2=192.168.1.102:2888:3888
server.3=192.168.1.103:2888:3888
2888:用于集群内部的消息传递。3888:用于集群节点之间的选举。
5.4 创建数据存储目录:每个节点都需要有 dataDir 目录来存储 Zookeeper 的数据。你可以创建如下目录并设置权限:
sudo mkdir -p /var/lib/zookeeper
sudo chown zookeeper:zookeeper /var/lib/zookeeper
5.5 配置每个节点的 myid 文件:在每台机器上,Zookeeper 使用 myid 文件来标识其在集群中的节点 ID。该文件的内容为节点 ID(通常从 1 开始),并存放在 dataDir 目录下。对于节点 1,在 /var/lib/zookeeper 目录下创建 myid 文件,内容为 1:
echo 1 | sudo tee /var/lib/zookeeper/myid
对于节点 2,myid 文件内容为 2:
echo 2 | sudo tee /var/lib/zookeeper/myid
对于节点 3,myid 文件内容为 3:
echo 3 | sudo tee /var/lib/zookeeper/myid
确保每个节点的 myid 文件和 dataDir 目录具有正确的权限:
sudo chown zookeeper:zookeeper /var/lib/zookeeper/myid
6. 启动 Zookeeper 集群
6.1 启动每个节点:在每个节点上,使用以下命令启动 Zookeeper 服务:
sudo -u zookeeper /opt/zookeeper/zookeeper/bin/zkServer.sh start
6.2 检查节点状态:启动完成后,使用以下命令检查每个节点的状态:
sudo -u zookeeper /opt/zookeeper/zookeeper/bin/zkServer.sh status
输出应类似于以下内容,表示节点的状态:
Mode: leader (如果是集群中的主节点)
Mode: follower (如果是从节点)
Mode: standalone (如果是单节点模式)
6.3 验证集群状态:在任何一个节点上,使用 zkCli.sh 连接到 Zookeeper 集群并查看节点信息:
/opt/zookeeper/zookeeper/bin/zkCli.sh -server 192.168.1.101:2181
然后执行以下命令查看集群中所有的服务器:
stat
或者查看集群内部的 zookeeper 节点:
ls /zookeeper
你应该能够看到多个 Zookeeper 节点并且确认集群已经正常运行。
7. 配置 Zookeeper 为系统服务(可选)为了让 Zookeeper 在系统启动时自动启动,可以将其配置为 systemd 服务:
7.1 创建 zookeeper.service 文件:
sudo nano /etc/systemd/system/zookeeper.service
7.2 添加以下内容:
Description=Zookeeper Server
After=network.target
[Service]
User=zookeeper
Group=zookeeper
ExecStart=/opt/zookeeper/zookeeper/bin/zkServer.sh start
ExecStop=/opt/zookeeper/zookeeper/bin/zkServer.sh stop
ExecReload=/opt/zookeeper/zookeeper/bin/zkServer.sh restart
Restart=always
LimitNOFILE=4096
[Install]
WantedBy=multi-user.target
7.3 重新加载 systemd 配置并启用 Zookeeper 服务:
sudo systemctl daemon-reloadsudo systemctl enable zookeeper
sudo systemctl start zookeeper
8. 监控和维护
监控:使用 zkCli.sh 工具定期检查集群状态。
备份:定期备份 Zookeeper 数据。
日志:检查 /opt/zookeeper/zookeeper/logs 目录下的日志文件,确保没有错误或警告。
往期推荐
开源的商业智能BI:Apache Superset介绍&安装