ZooKeeper 指南

ZK 分布式协调服务介绍

ZK 简介

官方介绍

ZooKeeper 是一种集中式服务,用于维护配置信息,命名,提供分布式同步
和提供组服务。所有这些类型的服务都以分布式应用程序的某种形式使用。
每次实施它们都需要做很多工作来修复不可避免的错误和竞争条件。由于难
以实现这些类型的服务,应用程序最初通常会吝啬它们,这使得它们在变化
的情况下变得脆弱并且难以管理。即使正确完成,这些服务的不同实现也会
在部署应用程序时导致管理复杂性。

通俗理解

Zookeeper 是一个分布式协调服务,就是为用户的分布式应用程序提供协调
服务。只要半数以上的节点存活, Zookeeper 就能正常提供服务。 
Zookeeper  在底层管理(存储、读取)用户提交的数据,为数据提供节点
监听的服务。

分布式协调框架

分布式框架的好处

可靠性: 一个或几个节点的崩溃不会导致整个集群的崩溃
可伸缩性: 可以通过动态添加主机的方式以及修改少量配置文件,以便提升集群性能
透明性: 隐藏系统的复杂性,对用户体现为一个单一的应用

分布式框架的弊端

竞态条件:一个或多个主机尝试运行一个应用,但是该应用只需要被一个主机所运行
死锁: 两个进程分别等待对方完成
不一致性: 数据的部分丢失

分布协调服务,解决分布式服务在工作时产生的问题

  1. 竞态条件(多个主机同时对一个文件进行操作,俗称抢资源)
  2. 死锁(多个主机互相等待对方完成)
  3. 不一致性(资源文件丢失或者主机宕机)

典型应用场景: Hadoop 高可用的自动容灾

ZK 的作用

名字服务    //标识集群中的所有节点,(节点能够向其注册并产生唯一标识)
配置管理    //存储配置文件,以便共享                                
集群管理    //添加或删除节点同时,实时更新集群信息                  
选举机制                                                          
锁和同步服务    //当文件进行修改,会将其进行加锁,防止多用户同时写入    
高有效性数据注册

ZK 集群的安装部署

节点说明

Zookeeper 安装在 s102、s103、s104上,这三个节点同时是 Hadoop 的 DataNode

ZK 本地模式安装配置

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
# 0.安装配置在s101

# 1.解压 Zookeeper 安装包到指定目录
tar -xzvf zookeeper-3.4.10.tar.gz -C /soft/

# 2.为 Zookeeper 创建符号链接
ln -s zookeeper-3.4.10/ zk

# 3.为 Zookeeper 配置环境变量
sudo nano /etc/profile

export ZK_HOME=/soft/zk
export PATH=$PATH:$ZK_HOME/bin

# 4.使环境变量生效
source /etc/profile

# 5.将 zk/conf/zoo_sample.cfg 重命名或复制一份命名为 zoo.cfg
mv zoo_sample.cfg zoo.cfg

cp zoo_sample.cfg zoo.cfg

# 6.启动 Zookeeper
zkServer.sh start

ZK 完全分布式安装配置

脚本 xcall.sh

脚本 xsync.sh

脚本位置

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
# 1.修改 zoo.cfg 文件,指定工作目录,
dataDir=/home/centos/zookeeper

server.102=s102:2888:3888
server.103=s103:2888:3888
server.104=s104:2888:3888

# 2.将 Zookeeper 文件夹同步到其他节点
xsync.sh /soft/zookeeper-3.4.10
xsync.sh /soft/zk

# 3.使用 root 权限,将环境变量同步到其他节点
su root
xsync.sh /etc/profile
exit

# 4.在 s102-s104 中创建文件夹 /home/centos/zookeeper,并在文件夹内创建文件 myid
xcall.sh "mkdir /home/centos/zookeeper"

ssh s102 "echo 102 > /home/centos/zookeeper/myid"
ssh s103 "echo 103 > /home/centos/zookeeper/myid"
ssh s104 "echo 104 > /home/centos/zookeeper/myid"

# 5.按顺序启动 s102-s104 的 Zookeeper,分别在 s102、s103、s104 上执行
source /etc/profile; zkServer.sh start

# 5.1 开启远程主机 Zookeeper 客户端
zkCli.sh -server s102:2181

# 6.查看状态,可以看出 leader、follower
zkServer.sh status

配置 Hadoop 高可用的自动容灾

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
# 0.关闭 Hadoop

stop-all.sh

# 1.修改 hdfs-site.xml

<property>
<name>dfs.ha.automatic-failover.enabled</name>
<value>true</value>
</property>

# 2.修改 core-site.xml

<property>
<name>ha.zookeeper.quorum</name>
<value>s102:2181,s103:2181,s104:2181</value>
</property>

# 3.分发配置文件

xsync.sh /soft/hadoop/etc/hadoop/hdfs-site.xml

xsync.sh /soft/hadoop/etc/hadoop/core-site.xml

# 4.初始化zk
hdfs zkfc -formatZK

# 5.启动 HDFS
start-dfs.sh

# 6.启动 Zookeeper 命令行脚本 zkCli.sh
zkCli.sh



# 7.正常配置启动的进程,通过 xcall.sh jps 查看

==================== s101 jps ===================
1782 Jps
1418 NameNode
1725 DFSZKFailoverController
==================== s102 jps ===================
1185 DataNode
1288 JournalNode
1368 Jps
1067 QuorumPeerMain
==================== s103 jps ===================
1158 DataNode
1063 QuorumPeerMain
1261 JournalNode
1341 Jps
==================== s104 jps ===================
1141 DataNode
1321 Jps
1244 JournalNode
1053 QuorumPeerMain
==================== s105 jps ===================
1056 NameNode
1235 Jps
1164 DFSZKFailoverController

# 8.通过关闭 s101 的 NameNode 进程验证Hadoop 高可用的自动容灾
通过网页可以看出 s105 的状态为 active ,实现了自动容灾

# 9.查看 Hadoop 高可用文件
[zk: s102:2181(CONNECTED) 2] ls /hadoop-ha/mycluster
[ActiveBreadCrumb, ActiveStandbyElectorLock]
[zk: s102:2181(CONNECTED) 3] get /hadoop-ha/mycluster/ActiveBreadCrumb

myclusternn1s101

[zk: s102:2181(CONNECTED) 4] get /hadoop-ha/mycluster/ActiveStandbyElectorLock

myclusternn1s101

# ActiveStandbyElectorLock是临时结点,负责存储active状态下的节点地址

# ActiveBreadCrumb是永久结点,负责在zk会话关闭时,下一次启动状态下正确分配active节点,避免脑裂(brain-split),即两个active节点状态

ZK 数据结构、命令

ZK 数据结构

Zookeeper 特性:

  1. Zookeeper 文件系统以 / 为根目录,文件系统为树形结构,每一个目录我们称之为结点
  2. Zookeeper 不存文件,只存数据
  3. 每个结点(znode)存放的数据最多1M

ZK 命令

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
# 进入 Zookeeper 客户端
zkCli.sh

# 查看帮助
help

# 列出根结点下的子结点
ls /

# 查看结点上存储的数据
get /

# 获取指定节点的状态(无数据)
stat

# 在根结点写入数据tom
set / 'tom'

# 创建有数据结点
create /a 'tomas'

# 创建无数据结点
create /b ''

# 删除没有子结点的结点
delete /b

# 递归删除结点
rmr /a

# 退出客户端
quit

ZK API 的使用

Demo

编写 xzk.sh 脚本

1
2
3
4
5
6
7
#!/bin/bash
for((i=102 ; i<=104; i++)) ; do
tput setaf 2
echo ==================== s$i $1 ===================
tput setaf 9
ssh s$i "source /etc/profile ; zkServer.sh $1"
done

编写 xzk.sh 脚本,是为了方便在 s101 节点上启动所有的 Zookeeper 进程

可执行的命令为:

  1. xzk.sh start
  2. xzk.sh stop
  3. xzk.sh status

ZK 的原理以及选举机制

ZK 的读写操作

  1. 读操作:所有zk节点都可以提供读请求(包括follower和leader)

  2. 写操作:需要先通过leader节点,leader同意之后,可以向指定节点写入

ZK 的选举机制

Zookeeper 虽然在配置文件中并没有指定 master 和 slave,但是 Zookeeper 工作时,是有一个节点为 leader,其他则为 follower

Leader是通过内部的选举机制临时产生的

Zxid: ZooKeeper 的事务 id,每次处理请求(读或写),此 id 会 +1
myid: 在配置时指定的 Zookeeper id

初始化选举

3个节点组成的 ZooKeeper 集群,myid 分别为102、103、104

  1. 启动 s102 ,选举状态为 looking 状态,
  2. 启动 s103 ,和 s102 进行通信,交换选举结果,根据 myid 的大小确认 s103 为 leader
  3. 启动 s104 ,和 s102 、s103 进行通信,交换选举结果,虽然 s104的 myid 的大于 s103 ,但是 s103 获得了一半以上的选票,s103 还是 leader

    非全新集群选举机制

适用于 ZooKeeper 节点故障之后的重新选举

  1. 先比较 Zxid ,Zxid 大的胜出
  2. Zxid 相同的情况下, myid 大的胜出
------ 本文结束------
如果对您有帮助的话请我喝瓶水吧!