01前言
根据ZooKeeper官网定义:ZooKeeper是一个集中式服务,用于维护配置信息、命名、提供分布式同步和提供组服务。分布式应用程序以某种形式使用所有这些类型的服务。每次实现它们时,都需要做大量工作来修复不可避免的错误和竞争条件。由于难以实现这些类型的服务,应用程序最初通常会忽略这些服务,这使得它们在发生变化时变得脆弱,难以管理。即使做得正确,在部署应用程序时,这些服务的不同实现也会导致管理复杂性。
02数据一致性级别
分布式系统中,分布式系统的数据一致性级别有以下几种:
1、强一致性
这种一致性级别是最符合用户直觉的,它要求系统写入什么,读出来的也会是什么,用户体验好,但实现起来往往对系统的性能影响比较大。
2、弱一致性
这种一致性级别约束了系统在写入成功后,不承诺立即可以读到写入的值,也不具体承诺多久之后数据能够达到一致,但会尽可能地保证到某个时间级别后,数据能够达到一致性状态,弱一致性还可细分为:
会话一致性:该一致性级别只保证对于写入的值,在同一个客户端会话中可以读到一致的值,但其他用户的会话不能保证。
用户一致性:该一致性级别只保证对于写入的值,在同一个用户中可以读到一致的值,但其他用户不能保证。
3、最终一致性
最终一致性是弱一致性的一个特例,系统会保证在有一定时间内,能够达到一个数据一致的状态,这里之所以将最终一致性单独提出来,是因为它是弱一致性中非常重要的一种一致性模型,也是业界在大型分布式系统的数据一致性上比较推崇的模型。
03分布式CAP/BASE理论
3.1 ACID
事务是由一系列对系统中数据进行访问与更新的操作所组成的一个程序执行逻辑单元,狭义上的事务特指数据库事务。
事务的四个基本特征:原子性(Atomicity)、一致性(Consistency)、隔离性(Isolation)、持久性(Durability),简称事务的ACID特性。
具体见另一篇文章详解:听说面试官喜欢问这些MySQL知识
3.2 分布式事务
分布式事务是指事务的参与者、支持者的服务器、资源服务器以及事务管理器分别位于分布式系统的不同节点之上。通常一个分布式事务中会涉及对多个数据源或业务系统的操作。
分布式事务也可以被定义为一种嵌套型的事务,同时也就具有了ACID的事务特性。
3.3 CAP和BASE理论
CAP定理:
CAP理论告诉我们,一个分布式系统不可能同时满足一致性(C:Consistency)、可用性(A:Availability)和分区容错性(P:Partition tolerance)这三个基本需求,最多只能同时满足其中的两项。BASE理论:BASE是Basically Available(基本可用),Soft state(软状态)和Eventually consistent(最终一致性)三个短语的简写,是由来自eBay的架构师Dan Pritchett提出的。BASE是对CAP中一致性和可用性权衡的结果,其来源于对大规模互联网系统分布式实践的总结,是基于CAP定理逐步演化而来的,其核心思想是即使无法做到强一致性,但是每一个应用都可以根据自身的业务特点,采用适当的方式来使系统达到最终一致性。
详细见另一篇文章:分布式CAP理论和BASE理论
04数据一致性级别
为了解决分布式一致性的问题,在长期的探索研究过程中,涌现出了一大批经典的一致性协议和算法,其中最著名的就是二阶段提交协议、三阶段提交协议和Paxos算法。
4.1 2PC
2PC是Two-Phase Commit的缩写,即二阶段提交,是计算机网络尤其是在数据库领域内,为了使基于分布式系统架构下的所有节点在进行事务处理过程中能够保持原子性和一致性而设计的一种算法。
二阶段协议也被认为是一种一致性协议,用来保证分布式系统数据的一致性。
简单的讲,二阶段提交就是将一个事物的处理过程分为了投票和执行两个阶段,其核心是对每个事务都采用先尝试后提交的处理方式,也可以将二阶段提交看做是一个强一致性的算法。
优点:原理简单,实现方便。
缺点:同步阻塞、单点问题、脑裂、太过保守。
4.2 3PC
3PC是在2PC的基础上进行的改进而提出的三阶段提交协议。是Three-Phase Commit的缩写,即三阶段提交,将二阶段提交协议的“提交事务请求”过程一分为2,形成了由CanCommit、PreCommit和do Commit三个阶段组成的事务处理协议。
需要注意得是,一旦进入阶段三,可能会出现以下两种故障:
- 协调者出现问题
- 协调者和参与者之间的网络出现故障
无论出现哪种情况,最终都会导致参与者无法及时接收来自协调者的doCommit或者是abort请求,针对这样的异常情况,参与者都会在等待超时之后,继续进行事务提交操作。
优缺点:
三阶段提交协议的优点:相较于二阶段的提交协议,三阶段提交协议最大的优点是降低了参与者的阻塞范围,并且能够出现单点故障后继续达成一致。
三阶段提交协议的缺点:三阶段提交协议在去除阻塞的同时也引入了新的问题,那就是在参与者接收到preCommit消息后,如果网络出现分区,此时协调者所在的节点和参与者无法进行正常的网络通信,在这种情况下,该参与者依然会进行事务的提交,这必然出现数据得到不一致性。
05Paxos算法
5.1Paxos理论的诞生
Paxos算法是莱斯利*兰伯特于1990年提出的一种基于消息传递且具有高度容错特性的一致性算法,是目前公认的解决分布式一致性问题的最有效算法之一。
当发生机器宕机或网络异常等情况时,Paxos算法可以解决因为发生这类异常时,可以快速且正确的在集群内部对某个数据的值达成一致,并且保证不论发生以上任何异常,都不会破坏整个系统的一致性。
5.2Paxos算法详解
小结:
三种一致性协议2PC、3PC、Paxos都是非常优秀的分布式一致性协议,从不同的方面不同程度地解决了分布式数据一致性的问题,使用范围广泛。2PC协议解决了分布式事务的原子性问题,保证了分布式事务的多个参与者要么都执行成功,要么都执行失败。二阶段协议依然存在:同步阻塞、无限期等待和“脑裂”问题,3PC三阶段协议在二阶段协议基础上,添加了PreCommit过程,从而避免了2PC协议中的无限期等待问题。Paxos协议引入了“过半”的理念,通俗地讲就是少数服从多数原则,同时也支持分布式节点角色之间的轮换,极大的避免了分布式单点的出现,Paxos既解决无限期等待问题,也解决了“脑裂”问题,是目前来说最优秀的分布式一致性协议之一。
06ZAB协议
6.1ZAB协议介绍
Zookeeper并非完全采用Paxos算法,采用的是一种称为Zookeeper Atomic BroadCast(ZAB Zookeeper原子消息广播协议)的协议来作为其数据一致性的核心算法。
ZAB是为分布式协调服务Zookeeper专门设计的一种支持崩溃恢复的原子广播协议。
ZAB协议包括两种基本的模式,分别是崩溃恢复和消息广播。当整个服务框架在启动过程中,或是当Leader服务器出现中断、崩溃退出与重启等异常情况时,ZAB协议就会进入恢复模式并选举产生Leader服务器。当选举产生了新的Leader服务器,同时集群中已经有过半机器与该Leader服务器完成了状态同步之后,ZAB协议就会退出恢复模式。状态同步就是指数据同步,用来保证集群中存在过半的机器能够和Leader服务器的数据状态保持一致。
6.2 ZAB与Paxos算法的联系与区别
ZAB协议并不是Paxos算法的一个典型实现,ZAB和Paxos之间的联系:
- 两者都存在一个类似于Leader进程的角色,由其负责协调多个Follower进程的运行。
- Leader进程都会等待超过半数的Follower做出正确的反馈后,才会将一个提案进行提交。
- 在ZAB协议中,每个Proposal中都包含了一个epoch值,用来代替当前的Leader周期,在Paxos算法中同样存在这样一个标识,它是Ballot。
Paxos算法中,一个新选举产生的主进程会进行两个阶段的工作。第一个阶段被称为读阶段,在这个阶段中,这个新的主进程会通过和所有其他进程进行通信的方式来收集上一个主进程提出的提案,并将它们提交。第二阶段被称为写阶段,在这个阶段,当前主进程开始提出它自己的提案。在Paxos算法的设计基础上,ZAB协议额外添加了一个同步阶段,在同步阶段之前,ZAB协议也存在一个和Paxos算法中的读阶段类似的过程,称为发现阶段。同步阶段中,新的Leader会确保存在过半的Follower已经提交了之前Leader周期中的所有事物Proposal。这一同步阶段的引入,能够有效地保证Leader在新的周期中提出事物Proposal之前,所有的进程都已经完成了对之前所有事物Proposal的提交,一旦完成同步阶段后,ZAB就会执行和Paxos算法类似的写阶段。
ZAB和Paxos算法的本质区别在于,两者的设计目标不太一样。ZAB协议主要用于构建一个高可用的分布式数据主备系统,如Zookeeper,而Paxos算法则是用于构建一个分布式的一致性状态机系统。
07Zookeeper的应用场景
7.1 发布/订阅
数据发布/订阅(publish/Subcribe)系统,即所谓的配置中心,顾名思义就是发布者将数据发布到Zookeeper的一个或一系列节点上,供订阅者进行数据订阅,进而达到动态获取数据的目的,实现配置信息的集中式管理和数据的动态更新。
7.2 负载均衡
负载均衡(Load Balance)是一种相当常见的算计网络技术,用来对多个计算机、网络连接、CPU、磁盘驱动器或其他资源进行分配负载,以达到优化资源使用、最大化吞吐率、最大化响应时间和避免过载的目的。通常负载均衡可以分为硬件和软件负载均衡两类。
7.3分布式协调通知
分布式系统中,对于一个在多态机器上部署运行的应用而言,通常需要一个协调者,来控制整个系统的运行流程。如分布式事务的处理,机器间的互相协调等。引入这样一个协调者,便于将分布式协调的职责从应用中分离出来,从而可以大大减少系统之间的耦合性,而且能够显著提高系统的可扩展性。
7.4集群管理
集群管理,包括集群监控与集群控制两大块,前者侧重对集群运行时状态的收集,后者则是核对集群进行操作与控制,类似如下日常工作需求:
- 希望知道当前集群中究竟有多少机器在工作。
- 对集群中每台机器的运行时状态进行数据收集。
- 对集群中机器进行上下线操作。
7.5Master选举
Master选举是一个在分布式系统中非常常见的应用场景。分布式最核心的特性就是能够将具有独立计算能力的系统单元部署在不同的机器上,构成一个完整的分布式系统。在分布式系统中,Master往往用来协调集群中其他系统单元,具有对分布式系统状态变更的决定权。在一些读写分离的应用场景中,客户端的写请求往往由Master来处理的,另一些场景中,Master则常常负责处理一些复杂的逻辑,并将处理结果同步给集群中其他系统单元。
7.6分布式锁
分布式锁是控制分布式系统之间同步访问共享资源的一种方式。如果不同的系统或是同一个系统的不同主机之间共享一个或一组资源,那么访问这些资源的时候,往往需要通过一些互斥手段来防止彼此之间的干扰,以保证一致性,这种情况下,需要分布式锁。
Zookeeper的分布式锁是定义了一个排它锁来实现:Zookeeper上的数据节点/exclusive_lock/lock监听客户端的,当客户端需要获取排它锁时,试图通过调用create()接口,在/exclusive_lock节点下创建临时子节点/exclusive_lock/lock。没有获取到这个子节点的客户端注册一个Watcher监听的节点,实时监听lock节点的变更情况。
7.7分布式队列
业界通常有不少专业分布式队列产品,类似于ActiveMQ、Kafka、RabbitMQ等消息中间件,详细查看另一篇文章:
Zookeeper实现分布式队列有2种,一种是:FIFO先入先出,另一种是:Barrier 分布式屏障
参考资料文献:《从Paxos到Zookeeper 分布式一致性原理与实战》