Zookeeper——入门介绍(相关原理、安装启动及使用操作)

Zookeeper——入门介绍(相关原理、安装启动及使用操作)
关注微信公众号:CodingTechWork,一起学习进步。

引言

  对zk的学习和简单使用进行一个总结。

zk介绍

zk概述

  1. zk是一个具有高可用性的高性能协调服务。
  2. zk的watcher对象有两个作用:一方面是用于获得zk状态变化的通知;另一方面是用于获得znode变化的相关通知。

zk特点

  1. zk是简单的,核心是一个精简的文件系统,提供诸如排序和通知等简单的操作和额外的抽象操作。
  2. zk是富有表现力的,zk的基本操作是一组丰富的构件,可用于实现多种协调数据结构和协议,如分布式队列、分布式锁和一组节点的“领导者选举”。
  3. zk具有高可用性,可以帮助系统避免出现单点故障,从而构件一个可靠的应用程序。
  4. zk采用松耦合交互方式,交互过程中,参与者可不需要彼此了解,如zk可被用于实现“数据汇集”机制,让进程在不了解其他进程(或网络)情况下能够彼此发现并进行信息交互。一个进程可以在zk中留下一条消息后关闭,另外一个进程还可以继续读取这条消息。
  5. zk是一个资源库,提供一个通用协调模式实现方法的开源共享库。
  6. zk是高性能的,基准吞吐量超过每秒10000个操作。

zk数据模型

数据模型特点

  1. 树形节点:zk维护一个树形层次结构,树中的节点被称为znode。znode可以用于存储数据,并且有一个与之相关联的ACL
  2. 小数据存储:zk被设计用来实现协调服务,通常使用小数据文件,而不是用于大容量数据存储,一个znode能存储的数据被限制在1MB以内。
  3. 原子性数据访问:zk的数据访问具有原子性。客户端读取一个znode的数据时,要么读到所有数据,要么读操作全部失败(不会存在读取部分数据这种状态)。同样,写操作也是一样,要么全部调换znode存储数据,要么写不成功而失败,不会出现部分写现象。
  4. 路径引用:znode通过路径被引用,路径用斜杠分割的Unicode字符串,路径必须是绝对路径,每条路径从一个斜杠字符开始。路径引用中不包含“.”这种不合法表示,不支持路径解析。hadoop是通过URI,如hdfs://ns1/user/userA
  5. "zookeeper"字符串是一个保留词,不能作为路径表示中的一部分。zk中使用/zookeeper子树保存管理信息

znode

znode概念

  1. zk可以看作是一个具有高可用性特征的文件系统,没有文件和目录,而是使用“节点”概念,称为znode,znode既可以作为保存数据的容器(类似于文件),也可以作为保存其他znode的容器(类似于目录)
  2. 所有znode构成一个层次化的命名空间,创建一个以组名为节点名的znode作为父节点,然后以组成员名(服务器名)为节点名来创建作为子节点的znode。
    Zookeeper——入门介绍(相关原理、安装启动及使用操作)

znode分类

  znode分为短暂和持久两种大类型。类型在创建时被确定且后面不能再修改。
Zookeeper——入门介绍(相关原理、安装启动及使用操作)

短暂znode

  1. 在创建短暂znode的客户端会话结束时,zk会将该短暂的znode删除。在创建持久znode时,不依赖于客户端会话,只有客户端明确要删除znode时,才会被删除。
  2. 短暂znode不可以有子节点。
  3. 短暂znode都会被板顶到一个客户端会话,但对所有客户端可见。
  4. 短暂znode应用:使用短暂znode来实现一个组成员管理服务,让任何进程都知道在特定的时刻有哪些组成员可用。

顺序znode

  1. 顺序znode是指名称中包含zk指定顺序号的znode,若在创建znode时设置了顺序标识,则该znode名称之后会附加一个值,这个值是由一个单调递增的计数器(由父节点维护)所添加的。

观察机制

  1. 观察机制通知客户端znode的变化。
  2. 可以针对zk服务的操作设置观察,如客户端A可以对一个znode调用exists操作,设定一个观察,若znode不存在,客户端A调用exists操作返回false。过段时间后,若另外一个客户端B创建了这个znode,观察被触发,通知前一个客户端A这个znode被创建。
  3. 观察只能被触发一次,若想多次收到观察通知,客户端需要重注册所需要的观察。

zk实现

zk运行模式分类

  1. 独立模式:只有一个zk服务器,简单,适合测试环境,不能保证高可用性和可恢复性。
  2. 复制模式奇数个服务器,运行一个计算机集群上,这个计算机集群被称为一个集合体,zk通过复制来实现高可用性,只要集合体中半数以上的机器处于可用状态,就能够提供服务。对znode树的每一个修改都会被复制到集合体中超过半数的机器上。

zk服务器为何是奇数个?

  因为zk生产环境一般是使用复制模式,即集合体中半数以上的机器处于可用状态,zk就可以继续提供服务,比如在一个有5个节点的集合体中,任意2台机器故障,都可以保证服务继续。而在6个节点的集合体里,只能够容忍2台机器出现故障,如果出现3台机器,剩下3台机器没有超过集合体的半数,无法判断是否可用。

zk实现原理

  zk使用了Zab协议,经历领导者选举原子广播两个循环重复的阶段。

  1. 领导者选举:集合体中的所有机器通过一个选择过程选出一台被称为领导者(leader)的机器,其他机器称为跟随者(follower),一旦半数以上的跟随者将其状态与领导者同步了,则表明该阶段完成。
  2. 原子广播:所有的写请求都会被转发给领导者,再由领导者更新广播给跟随者,当半数以上的跟随者已经将修改持久化后,领导者才会提交这个更新,客户端会收到一个更新成功的响应。

如果领导者机器出现故障,则剩余机器会选出一个新的领导者机器。若旧领导者恢复正常,会变成一个跟随者。一般选举只需要200毫秒

zk数据一致性

客户端连接到哪一台机器?

Zookeeper——入门介绍(相关原理、安装启动及使用操作)
  一个跟随者有可能滞后于领导者几个更新,而每个客户端都有可能被连接到领导者,但客户端对此无法控制,无法知道自己是否连接到领导者机器。所以客户端最好是全部连接到领导者机器,若实现不了,最好不要连接到领导者机器。对zk进行配置,使得领导者不接受任何客户端连接,领导者任务就变成了协调更新,可以将leaderServes属性设置为no来实现,推荐操作3台服务器的集群中使用该配置。

zxid

  1. 每一个对znode树的更新都被赋予一个全局唯一的ID,即为zxid(ZooKeeper Transaction ID)
  2. zk要求对所有的更新进行编号排序,决定了分布式系统的执行顺序。

数据一致性的保证

  1. 顺序一致性:来自任意特定客户端的更新都会按照其发送顺序被提交。如znode a值改为b,然后b值改为c,则其他所有客户端看到c后,都不会看到b值。(如果没有客户端对a值更新)执行是有顺序的。
  2. 原子性:每个更新要么成功,要么失败。若一个更新失败,不会有客户端看到这个更新的结果。
  3. 单一系统映像:一个客户端无论连哪台机器,都看到同样的系统视图。若一个客户端在同一个会话中连接到一台新服务器,所看到的系统状态不会比上一个服务器上所看到的更老。若一台服务器A出现故障,它的客户端尝试连接其他服务器时,所有状态滞后于服务器A的都不会接受该连接请求,而是去连接状态超前或同于服务器A的机器。
  4. 持久性:一个更新一旦成功,其结果就会持久存在且不会被撤销,所以更新操作不会受到服务器故障的影响。
  5. 及时性:任何客户端的滞后性有限,一般是不超过几十秒。由于性能要求,所有的读操作都是从zk服务器的内存中读数据,不参与写操作的全局排序。

ZK会话

会话介绍

  1. 每个zk客户端的配置中都包含集合体服务器列表,在启动时,客户端会尝试连接列表中的一台服务器,若连接失败,会尝试连接列表中其他服务器,一直练到成功或者全部连不上而失败。
  2. 客户端一旦和zk服务器建立连接,这台服务器就会为该客户端创建一个新的会话,每个会话都有一个超时时间的设置,由创建会话的应用来设定。若服务器在超时时间内没有收到任何请求,相应的会话会过期。一旦过期,则无法重新打开。
  3. 一个会话空闲超过一段时间,可以通过客户端发送ping请求来保持会话不过期(ping请求由zk的客户端库自动发送),这个时间足够低,监测出服务器故障,zk客户端会自动进行故障切换,切换到另一台服务器,会话有效。切换过程中的客户端其他操作会失败。

时间

  1. “滴答时间”:tick time定义了zk的基本时间周期,被集合体的服务器用来定义相互交互的时间表。
  2. 会话超时值设置基于滴答时间,大于等于2个滴答时间,小于等于20个滴答时间。如通常滴答参数设为2秒(2000毫秒),则会话超时时间为4-40秒
  3. 会话超时时间若设置太短,会较快监测到机器故障,但是要避免设置太低,繁忙的网络会导致数据包传输延迟,导致会话过期,机器会出现“振动(flap)”现象,即在很短的时间内反复出现离开后又重新加入组的情况。
  4. 会话超时时间设置大一点时,适用于重建会话代价较大的应用程序客户端,比如对应用进行维护或升级时,超时时间大,重启应用程序,也可以避免会话过期(重启时,未检测会话是否过期,避免过期),服务器会为每个会话分配一个唯一的ID和密码,建立连接过程中传递给zk,可以用于恢复一个会话。
  5. 一般zk的集合体服务器越多,会话超时的设置越大。可使用jmx监控zk度量指标,频繁遇到丢连接时,要考虑增大超时的设置。

状态

Zookeeper——入门介绍(相关原理、安装启动及使用操作)
zk对象在生命周期中可以通过getState()方法查询对象的状态,返回值States是zk对象不同状态的枚举类型值。

  1. 建立连接过程中,zk实例处于CONNECTING状态,建立连接完成后,进入CONNECTED状态。通过注册观察对象,进入CONNECTED后,观察对象会收到一个WatchedEvent通知,KeeperState值为SyncConnected
  2. zk实例在断开然后重连zk服务,状态就会在CONNECTED和CONNECTING之间转换。若断开连接会收到一个Disconnected事件。(重连是zk自动发起)
  3. 若调用close()方法或者出现会话超时(观察事件KeeperState的值为Expired时),zk实例会转换到第三个状态CLOSED。zk对象不再被认为是活跃的(通过State使用isAlive()方法判断),且不能再用。

zk应用

配置服务

  配置服务是分布式应用中的基本服务之一,使集群中的机器可以共享配置信息中公共部分。zk可以作为一个具有高可用性的配置存储器,允许分布式应用的参与者检索和更新配置文件。

  1. 存储的配置数据是字符串,关键字是znode路径,每个znode上存储了一个键值对;
  2. 在任何时刻只有一个客户端执行更新操作,其他客户端负责观察。

锁服务

  分布式锁能够在一组进程之间提供互斥机制,使任何时刻只有一个进程可以持有锁。可以用于在大型分布式系统中实现领导者选举,在任何时间点,持有锁的那个进程就是系统的领导者。(不同于zk自身的领导者选举)

实现原理

使用顺序znode来为竞争锁的进程强制排序,zk是顺序的仲裁者,负责分配顺序号。

  1. 首先制定一个作为锁的znode,通常用它来描述被锁定的实体,称为/leader。
  2. 然后希望获得锁的客户端创建一些短暂顺序znode,作为锁znode的子节点。在任何时间点,顺序号最小的客户端持有锁。如2个客户端几乎同时创建znode,为/leader/lock-1和/leader/lock-2,则创建/leader/lock-1的客户端持有锁。若删除znode /leader/lock-1,则释放锁,创建/leader/lock-2的客户端会持有锁。

zk安装

安装流程

  1. 下载
    进入官网:https://zookeeper.apache.org/,点击【Project】—>【Releases】寻找合适的版本。
  2. 解压
tar xzf zookeeper-x.y.z.tar.gz
  1. 加入命令行路径
export ZOOKEEPER_HOME=~/sw/zookeeper-x.y.z
export PATH=$PATH:%ZOOKEEPER_HOME/bin
  1. 配置文件(主要)
配置 说明
zoo.cfg 一般放在conf子目录或者/etc/zookeeper子目录中,若设置环境变量ZOOCFGDIR,可以保存在该环境变量所指定的目录
tickTime=2000 指定zk基本事件单元(毫秒)
dataDir=/Users/tom/zookeeper dataDir指定zk存储持久数据的本地系统位置
clientPort=2181 指定zk用于监听客户端连接的端口
  1. 启动
zkServer.sh start

zk配置服务器ID

  1. zk服务器的集合体中,每个服务器都有一个数值型的ID,服务器ID在集合体中唯一,取值为1~255,通过一个名为myid的纯文本文件设定服务器的ID,保存在dataDir参数所指定的目录中。
    Zookeeper——入门介绍(相关原理、安装启动及使用操作)
  2. 为每台服务器设置ID,还需要将集合体中其他服务器ID和网络位置告诉所有服务器,通过以下方式设置:
    server.n=hostname:port:port
    其中,n是服务器的ID,第一个端口是跟随者用来连接领导者的端口,第二个端口用于领导者选举。举例:
    Zookeeper——入门介绍(相关原理、安装启动及使用操作)
    a)服务器在3个端口上进行监听:2888端口用于客户端连接;
    b)对于领导者而言,2888端口被用于跟随者连接;
    c)3888端口被用于领导者选举阶段的其他服务器连接。
  3. 流程:当一个zk服务器启动时,它读取myid文件用于确定自己服务器ID;然后,通过读取配置文件来确定应当在哪个端口进行监听;同时,确定集合体中其他服务器的网络地址。在客户端中,其实就是通过zookeeper1:2181、zookeeper2:2181和zookeeper3:2181作为主机字符串。

zk配置时间参数

Zookeeper——入门介绍(相关原理、安装启动及使用操作)
initLimit和syncLimit参数是强制的,都是以滴答参数(tickTime)的倍数进行度量。

  1. initLimit参数:设定所有跟随者与领导者进行连接并同步的时间范围。在设定的时间段内,半数以上的跟随者若未能完成同步,领导者便会放弃领导地位,进行另外一个领导者的选举。若经常发生这种情况,需要调大参数值。
  2. syncLimit参数:设定允许一个跟随者与领导者进行同步的时间。在设定的时间段内,一个跟随者未能完成同步,会自己重启。所有关联到跟随者的客户端则会连接到另外一个跟随者

zk操作

服务操作

操作 描述
create 创建一个znode(必须要有父节点)
delete 删除一个znode(不能有任何子节点)
exists 测试一个znode存在与否并且查询它的元数据
getACL、setACL 获取/设置一个znode的ACL
getChildren 获取一个znode的子节点列表
getData、setData 获取/设置一个znode所保存的数据
sync 将客户端的znode视图与zk同步

观察事件类型

Zookeeper——入门介绍(相关原理、安装启动及使用操作)

查看zk的连接数

  1. 查看zk的连接数的几种命令
netstat -na | grep 2181 | wc -l
netstat -an | grep -I 2181
echo stat | nc localhost 2181
  1. 查看最大连接数配置
echo conf | nc localhost 2181 | grep "max"

Zookeeper——入门介绍(相关原理、安装启动及使用操作)

查看znode节点列表

  1. 查看命令行帮助
./zkCli.sh -server localhost ls 
  1. 查看所有组
./zkCli.sh -server localhost ls /

Zookeeper——入门介绍(相关原理、安装启动及使用操作)
3. 查看具体组

./zkCli.sh -server localhost ls /brokers

Zookeeper——入门介绍(相关原理、安装启动及使用操作)

常用操作命令

操作 描述
get path [watch] 1. 获取指定节点信息(包括数据内容和节点状态信息);
2. 节点路径必须以/开头;
3. watch为可选参数,表示是否注册监听,若添加该参数,则其他客户端修改节点数据后,当前客户端可收到数据变更通知;
4. 示例:get /znodeget /znode watch
stat path [watch] 用于查看节点状态信息,与get命令类似。如stat /
set path data [version] 对指定znode添加内容,version表示可以指定的dataVersion
ls path [watch] 获取当前路径下的子节点列表(仅仅包含下一级子节点)
ls2 path [watch] ls的增强版,获取当前路径下的子节点列表(仅仅包含下一级子节点)以及当前节点下的状态信息
delete path [version] 删除指定节点,当指定节点下有子节点时,该节点无法删除
rmr path 增强版delete,可以递归删除指定节点
create [-s] [-e] path data acl 创建节点,-s表示顺序节点,-e表示临时节点,acl表示设置权限控制
sync path 强制同步,由于请求在半数以上的服务器上生效就表示此请求生效,name就会有一些服务器数据是旧的,sync可以强制这些服务器同步更新操作
setAcl path acl 设置节点acl,格式为:scheme:id:permissions
getAcl path 获取节点acl信息,如getAcl /node1
listquota path 显示节点配额
setquota [-n val1 -b val2] path
delquota [-n -b] path

zk端口监听命令

zk四字母组合命令

Zookeeper——入门介绍(相关原理、安装启动及使用操作)

使用示例

监听端口:使用ruok,代表Are you OK?
echo ruok | nc localhost 2181
返回结果为imok,代表I'm OK
Zookeeper——入门介绍(相关原理、安装启动及使用操作)

zk的ACL

ACL介绍

  1. 每个znode创建时都会带有一个ACL列表,其用于决定谁可以对该znode拥有哪些执行权限。
    a)zk的权限控制是基于每个znode的,需要对每个znode进行权限设置;
    b)每个znode支持多种权限设置;
    c)子节点不会继承父节点的权限,客户端有可能无权访问父节点,但是可能可以访问它的子节点。
  2. ACL依赖于zk的客户端身份验证机制:
    a)digest:通过用户名和密码识别客户端;
    b) sals: 通过kerberos认证来识别客户端;(klist -ktkinit -kt
    c)ip: 通过客户端的ip来识别客户端;
  3. ACL权限控制,可使用scheme:id:permission来识别:
    a)权限模式(scheme):鉴权策略;
    b)授权对象(id)
    c)权限(permission)

ACL详解

  1. scheme:zk内置一些权限控制方案,可以用以下方案对每个znode进行权限设置。
方案 说明
world 只有一个用户:anyone,代表所有人。(默认权限)
ip 使用ip地址认证
auth 使用已添加认证的用户认证
digest 使用用户名:密码方式认证
  1. id:授权对象id是指权限赋予的用户或者实体,如ip地址或者机器,授权模式schemoa与授权对象id的关系如下:
权限模式 授权对象
ip 通常是一个ip地址或者ip段,如"192.168.0.10"或"192.168.0.1/24"
digest 自定义,通常是“username:BASE64(SHA-1(username:password))”,如“userA:jfCYslg7DFSjtoeFAdfs7FD=”
world 只有一个id:anyone
super 与digest模式一致
  1. 权限permission
权限 ACL简写 说明
CREATE c 可以创建子节点,create
DELETE d 可以删除子节点(仅仅是下一级节点),delete
READ r 可以读取节点数据及显示子节点列表,getChildren、getData
WRITE w 可以设置节点数据,setData
ADMIN a 可以设置节点访问控制权限列表,setACL
命令 使用方式 描述
getAcl getAcl <path> 读取ACL权限
setAcl setAcl <path> <acl> 设置ACL权限
addauth addauth <scheme> <auth> 设置认证

refer by >
官网:https://zookeeper.apache.org
《Hadoop权威指南-第四版》

上一篇:分享一波阿里、字节、腾讯、美团等精选大厂面试题,人生转折!


下一篇:大牛手把手带你!java环境变量的配置步骤