原文地址:http://zookeeper.apache.org/doc/trunk/zookeeperOver.html#fg_zkPerfReliability
zookeeper:分布式应用的分布式协调服务
zookeeper是分布式的,分布式应用的开源协调服务,他提供了一组简单的原语使分布式应用可以建立在为同步、配置维护、群组以及命名等实现更高级别的服务上。它被设计为易于编程,并且在一个相似的目录树结构的文件系统之下使用了数据模型样式,它运行在java环境中,并且为java和c都有绑。
众所周知协调服务难以获得合适的,它们尤其容易失误比如竞态条件和死锁,zookeeper的目的是减轻分布式应用从头开始实现分布式协调服务的责任。
设计目标:
zookeeper是简单的。zookeeper允许分布式进程彼此之间通过一个共享的多层次的,类似于标准的文件系统的命名空间相互协调。命名空间由数据寄存器组成,在zookeeper中被称为znodes,并且这些节点类似于文件和目录。不同于典型的文件系统,他是为存储而设计,zookeeper数据保存在内存中意味着zookeeper可以实现高吞吐率和低延迟数。
zookeeper是被复制的。像它协调分布式进程,zookeeper的目的是复制一组被称为ensemble的主机。
组成zookeeper服务的服务器必须都了解彼此,它们在内存中维持了状态图,以及在持久存储中的事务日志和快照,只要大多服务器可用,zookeeper服务就是可用的。
客户端连接到单一的zookeeper服务,客户端就维持了TCP连接,通过他发送请求,获得响应、监视事件,如果到服务器的TCP连接中断,客户端将会连接到不同的服务器上。
zookeeper是有序的。zookeeper每个数字更新的标志都反映了zookeeper处理的顺序,随后的操作可以通过那个顺序实现更高级别的抽象,比如同步原语。
zookeeper速度快。它在读为主写工作上是尤其快的,zookeeper运行在上千台主机上,它在读上比写执行得更好,比率大概10:1.
数据模型和多层的命名空间
zookeeper提供的命名空间更像是一个标准的文件系统,一个名称是由分隔符分隔的路径元素序列,zookeeper的每一个命名空间的节点通过路径标识。
节点和短暂节点:
不像标准的文件系统,每一个在zookeeper域名空间的节点可以和它自身以及子节点有数据关联,它就像有一个文件系统允许一个文件也可以是一个目录。(zookeeper被设计存储协调数据:状态,信息,配置,定位信息等。因此存储在每个节点的数据通常很小,在B到KB之间),我们使用术语 znode使我们在谈论zookeeper数据节点时更清晰。
zookeeper维持了数据结构,包含了对数据,ACL修改以及时间戳的版本号,允许缓存验证和协调更新。每次znode数据变化,版本号就增加。比如,每当客户端检索数据,也会收到数据的版本号。
存储在一个域名空间中的每一个节点的数据的读写都是原子性的,读可以获取到关联的znode的所有数据字节,写则会替换所有的数据。每个节点有一个访问控制列表(ACL)限制谁可以做什么。
zookeeper也有短暂节点的概念,只要会话被创建这些节点就是活跃的,会话结束节点被删除,
条件更新和watches
zookeeper支持watches概念,客户端可以在一个节点上设置watch,当节点改变时watch将会被触发和删除,当watch被触发时,客户端接收到一个数据包表明节点已经改变。如果客户端和zookeeper其中一个服务器的链接中断,客户端将会接收到本地通知。这些可以被用来.....【待定】
保证:
zookeeper是快速且简单的。由于他的目标,尽管,是一个更复杂服务的基本建设,比如同步,提供一系列的保证,这些是:
-序列一致性——客户端的更新将会被应用到他们被发送的顺序上。
-原子性——更新成功或失败,没有部分结果。
-单系统映像——客户端将会看到服务的相同视图,无论连接到的是哪个服务器。
-可靠性——一旦更新被应用就会继续存在只到客户端覆盖更新。
-时效性——该系统的客户端视图保证在一定时间是最新的。
简单API:
zookeeper其中一个设计目标提供了一套非常简单的编程接口,因此,它仅支持这些操作:
create:在树的某个位置创建一个节点
delete:删除一个节点
exists:测试某个位置节点是否存在
get data:从一个节点中读数据
set data:写数据到一个节点
get children:获取一个节点的子节点列表
sync:等待数据被传播
实施:
zookeeper组件显示了zookeeper服务的高级别组件。随着请求处理器的异常,组成zookeeper服务的每一个服务器都会复制自己每个组件的副本。
复制的数据库是内存数据库,包含了所有数据树,为了可恢复性,更新被记录到磁盘,并且,写在它们被应用到内存数据库之前,先被序列化到磁盘。
每个zookeeper服务器服务的客户端,客户端连接到一个服务器提交请求,读请求是从每一个服务器数据库的本地副本中被服务。请求改变服务状态,写请求通过协商协议被处理。
作为协商协议的一部分,所有来自客户端的写请求被转发到一个称作leader单独的服务器。剩余的zookeeper服务器称为followers从leader接收到消息并同意交付,消息传送层负责在失败时更换leader并且同步leader和followers。
zookeeper使用了定制的原子消息传送协议,因为消息传递层是原子性的,zookeeper可以保证本地副本一致,当leader接收到写请求,它计算当写被应用的时候系统的状态是什么并且将其转换为一个捕捉新状态的任务。