Zookeeper简介
1. Introduction
ZooKeeper是一种为分布式应用所设计的高可用、高性能且一致的开源协调服务,它提供了一项基本服务:
分布式锁服务。由于ZooKeeper 的开源特性,后来我们的开发者在分布式锁的基础上,摸索了出了其他的使用方法:配置维护、组服务、分布式消息队列、分布式通知/协调等。
2. zookeeper Data Modal
2.1 Znodes
zookeeper的节点与文件系统很类似,每一个节点相当于一个文件目录,而节点数据就相当于保存在目录里的数据
Znode的数据主要包含以下三项
- Stat 描述znode的状态,权限等信息
- data znode保存的数据信息最大不超过1M
- children. 该znode下的子节点
2.1.1 节点的类型
- 临时节点 Ephemeral Nodes
依赖于session 一旦session关闭后临时节点将自动删除 - 持久节点 Persistent Nodes
会话结束后不会被删除,除非主动删除 - 序列节点 Sequence Nodes
当创建Znode的时候,用户可以请求在ZooKeeper的路径结尾添加一个递增的计数。这个计数对于此节点的父节点来说是唯一的,它的格式为”%10d”(10位数字,没有数值的数位用0补充,例如”0000000001″)。当计数值大于232-1时,计数器将溢出
2.2 Time in zookeeper
- Zxid
zookeerper的每一次状态更新都会以zxid(zookeeper的事务id)的形式收到一个戳记,这个戳记暴露了zookeeper的事务排序。每一次的更改都会有唯一的一个zxid,如果zxid1 < zxid2 说明zxid1在zxid2之前发生 - Version numbers
每一次的节点改变都会使得版本号增加,三个版本号分别对应着节点数据更新次数,子节点更新次数,以及节点的ACL列表更新次数 - Ticks
定义了session的超时时间 - Real time
除了将时间戳放入znode创建和znode修改的stat结构之外,zookeeper从不使用真实的时间
2.3 Zookeeper Stat Structure
2.3.1 结构介绍
- czxid. 节点创建时的zxid.
- mzxid. 节点最新一次更新发生时的zxid.
- ctime. 节点创建时的时间戳.
- mtime. 节点最新一次更新发生时的时间戳.
- dataVersion. 节点数据的更新次数.
- cversion. 其子节点的更新次数.
- aclVersion. 节点ACL(授权信息)的更新次数.
- ephemeralOwner. 如果该节点为ephemeral节点,ephemeralOwner值表示与该节点绑定的session id. 如果该节点不是ephemeral节点, ephemeralOwner值为0. 至于什么是ephemeral节点, 请看后面的讲述.
- dataLength. 节点数据的字节数.
- numChildren. 子节点个数
2.3.2 zxid介绍
- Zxid
致使ZooKeeper节点状态改变的每一个操作都将使节点接收到一个Zxid格式的时间戳,并且这个时间戳全局有序。也就是说,也就是说,每个对节点的改变都将产生一个唯一的Zxid。如果Zxid1的值小于Zxid2的值,那么Zxid1所对应的事件发生在Zxid2所对应的事件之前。实际上,ZooKeeper的每个节点维护者三个Zxid值,为别为:cZxid、mZxid、pZxid。
- cZxid: 是节点的创建时间所对应的Zxid格式时间戳。
- mZxid:是节点的修改时间所对应的Zxid格式时间戳。
- 实现中Zxid是一个64为的数字,它高32位是epoch用来标识leader关系是否改变,每次一个leader被选出来,它都会有一个 新的epoch。低32位是个递增计数
3. ZooKeeper Sessions
在client和server通信之前, 首先需要建立连接, 该连接称为session.建立会话链接, 连接建立后, 如果发生连接超时, 授权失败, 或者显式关闭连接, 连接便处于CLOSED状态, 此时session结束.
4. ZooKeeper Watches
客户端可以在节点上设置watch,我们称之为监视器。当节点状态发生改变时(Znode的增、删、改)将会触发watch所对应的操作。当watch被触发时,ZooKeeper将会向客户端发送且仅发送一条通知,因为watch只能被触发一次,这样可以减少网络流量。
特点:
- 一次触发:如果client消费了一次监听事件,如果不再次绑定监听,则下次则不会再触发监听事件
5. ZooKeeper access control using ACLs
权限的创建方式:Schemes:id:Permission
5.1 ACL权限概念
- CREATE 允许创建子节点
- READ 允许获取读取节点数据
- WRITE 允许写入节点数据
- DELETE 允许删除子节点
- ADMIN 允许设置权限
5.2 ACL Schemes
- world 有个唯一的id, anyone ,代表所有人。
[zk: localhost:2181(CONNECTED) 10] getAcl /zookeeper
'world,'anyone
: cdrwa
auth 不使用任何id,代表任何已认证的用户。
auth: 它不需要id, 只要是通过authentication的user都有权限(zookeeper支持通过kerberos来进行authencation, 也支持username/password形式的authentication)digest 用 username:password 字符串来产生一个MD5串,然后该串被用来作为ACL ID。认证是通过明文发送username:password 来进行的,当用在ACL时,表达式为username:base64 ,base64是password的SHA1摘要的编码。
digest scheme的id表示为username:BASE64(SHA1(password))
[zk: localhost:2181(CONNECTED) 0] create -e /taozhi01 "23"
Created /taozhi01
[zk: localhost:2181(CONNECTED) 1] create -e /taozhi02 "23" digest:test:V28q/NynI4JI3Rk54h0r8O5kMug=:crwda
Created /taozhi02
[zk: localhost:2181(CONNECTED) 2] get /taozhi02
Authentication is not valid : /taozhi02
[zk: localhost:2181(CONNECTED) 3] addauth digest test:test
[zk: localhost:2181(CONNECTED) 4] get /taozhi02
23
cZxid = 0x400000090
ctime = Tue Oct 17 16:51:09 CST 2017
mZxid = 0x400000090
mtime = Tue Oct 17 16:51:09 CST 2017
pZxid = 0x400000090
cversion = 0
dataVersion = 0
aclVersion = 0
ephemeralOwner = 0x5f13b3dee4002e
dataLength = 2
numChildren = 0
- ip 使用客户端的主机IP作为ACL ID 。这个ACL表达式的格式为addr/bits ,此时addr中的有效位与客户端addr中的有效位进行比对。
[zk: localhost:2181(CONNECTED) 1] create -e /taozhiming "123" ip:127.0.0.1:crwda
Created /taozhiming
[zk: localhost:2181(CONNECTED) 2] getAcl /taozhiming
'ip,'127.0.0.1
: cdrwa
[zk: localhost:2181(CONNECTED) 3] ls /taozhiming
[]
[zk: localhost:2181(CONNECTED) 4] get /taozhiming
123
cZxid = 0x400000086
ctime = Tue Oct 17 16:37:29 CST 2017
mZxid = 0x400000086
mtime = Tue Oct 17 16:37:29 CST 2017
pZxid = 0x400000086
cversion = 0
dataVersion = 0
aclVersion = 0
ephemeralOwner = 0x5f13b3dee4002a
dataLength = 3
numChildren = 0
[zk: localhost:2181(CONNECTED) 5]
Zookeeper quota
quota 用来限制节点
setquota -n/-d -n表示节点数 -d表示数据大小
但是即使节点超出限制也不会报错,所以当前不清楚具体用途
[zk: localhost:2181(CONNECTED) 25] setquota -n 2 /tao
Comment: the parts are option -n val 2 path /tao
[zk: localhost:2181(CONNECTED) 26] listquota /tao
absolute path is /zookeeper/quota/tao/zookeeper_limits
Output quota for /tao count=2,bytes=-1
Output stat for /tao count=1,bytes=0
[zk: localhost:2181(CONNECTED) 27] create /tao/tao01 ""
Created /tao/tao01
[zk: localhost:2181(CONNECTED) 28] create /tao/tao02 ""
Created /tao/tao02
[zk: localhost:2181(CONNECTED) 29] create /tao/tao03 ""
Created /tao/tao03
[zk: localhost:2181(CONNECTED) 30] create /tao/tao04 ""
Created /tao/tao04
zookeeper的常用命令
[zkshell: 0] help
ZooKeeper host:port cmd args
get path [watch]
ls path [watch]
set path data [version]
delquota [-n|-b] path
quit
printwatches on|off
create path data acl
stat path [watch]
listquota path
history
setAcl path acl
getAcl path
sync path
redo cmdno
addauth scheme auth
delete path [version]
deleteall path
setquota -n|-b val path