ZooKeeper的工作原理

 ZooKeeper是一个分布式的应用程序协调服务

 

2 ZooKeeper的工作原理

Zookeeper 的核心是原子广播,这个机制保证了各个Server之间的同步。实现这个机制的协议叫做Zab(Zookeeper Atomic Broadcast)协议。Zab协议有两种模式,它们分别是恢复模式(recovery选主) 广播模式(broadcast同步)。当服务启动或者在领导者崩溃后,Zab就进入了恢复模式,当领导者被选举出来,且大多数Server完成了leader状态同步以 后,恢复模式就结束了。状态同步保证了leaderServer具有相同的系统状态

 

 1ZooKeeper数据模型

类似于一个标准的文件系统具有层次关系的数据结构

每个子目录项如NameService都被称作为znode

ZNode根据其本身的特性,可以分为下面两类

Regular ZNode: 常规型ZNode

Ephemeral ZNode: (ɪ'fem(ə)r(ə)l)(临时的)类型的目录节点不能有子节点目录。

Zookeeper的客户端和服务器通信采用长连接方式,每个客户 端和服务器通过心跳来保持连接,这个连接状态称为session,如果znode是临时节点,这个session失效,znode也就删除了。(3s/一次,200)

如果Client因为TimeoutZookeeper Server失去连接,client处在CONNECTING状态,会自动尝试再去连接Server,如果在session有效期内再次成功连接到某个Server,则回到CONNECTED状态。

 

2ZooKeeper Watch

 

    Zookeeper从设计模式的角度来看,是一个基于观察者设计模式设计的。简单来说就是

 Client可以在某个ZNode上设置一个Watcher,来WatchZNode上的变化。如果该ZNode上有相应的变化,就会触发这个Watcher,把相应的事件通知给设置WatcherClient。需要注意的是,ZooKeeper中的Watcher是一次性的,即触发一次就会被取消,如果想继续Watch的话,需要客户端重新设置Watcher

 

3、 ZooKeeper特性 

 

   读、写(更新)模式

 

  ZooKeeper集群中,读可以从任意一个ZooKeeper Server写的请求会先ForwarderLeader,然后由Leader来通过ZooKeeper中的原子广播协议,将请求广播给所有的FollowerLeader收到一半以上的写成功的消息后,就认为该写成功了,就会将该写进行持久化,并告诉客户端写成功了。

 

   FIFO
对于每一个ZooKeeper客户端而言,所有的操作都是遵循FIFO顺序的,这一特性是由下面两个基本特性来保证的:一是ZooKeeper ClientServer之间的网络通信是基于TCPTCP保证了Client/Server之间传输包的顺序;二是ZooKeeper Server执行客户端请求也是严格按照FIFO顺序的。

了保证事务的顺序一致性,zookeeper采用了递增的事务id号(zxid)来标识事务。所有的提议(proposal)都在被提出的时候加上了 zxid。实现中zxid是一个64位的数字,它高32位是 用来标识leader关系是否改变,每次一个leader被选出来,它都会有一个新 的epoch,标识当前属于那个leader的统治时期。低32位用于递增计数。

 

 ZooKeeper典型应用场景

  1. 名字服务(NameService) 

每个ZNode都可以由其路径唯一标识,路径本身也比较简洁直观,另外ZNode上还可以存储少量数据,这些都是实现统一的NameService的基础。通过简单的名字,访问对应的服务器集群。

 

  1. 配置管理(Configuration Management) 

 

 

 

:分布式互斥锁 

在传统的应用程序中,线程、进程的同步,都可以通过操作系统提供的机制来完成。但是在分布式系统中,多个进程之间的同步,操作系统层面就无能为力了。

zookeeper中,并没有JAVA里一样有Synchronized或者是ReentrantLock机制来实现锁机制,但是在zookeeper中,实现起来更简单:我们可以讲将zk的一个数据节点代表一个锁,当多个客户端同时调用create()节点创建节点的时候,zookeeper会保证只会有一个客户端创建成功,那么我们就可以让这个创建成功的客户端让其持有锁,而其它的客户端则注册Watcher监听当持有锁的客户端释放锁后,监听的客户端就会收到Watcher通知,然后再去试图获取锁,这样反复即可。

Zookeeper的三种角色:

1.leaderfollower 

 

      ZooKeeper需要在所有的服务(可以理解为服务器)中选举出一个Leader,然后让这个Leader来负责管理集群。此时,集群中的其它服务器则 成为此LeaderFollower。并且,当Leader故障的时候,需要ZooKeeper能够快速地在Follower中选举出下一个 Leader。这就是ZooKeeperLeader机制,下面我们将简单介绍在ZooKeeper中,Leader选举(Leader Election)是如何实现的。 

此操作实现的核心思想是:首先创建一个EPHEMERAL目录节点,例如“/election”。然后。每一个ZooKeeper服务器在此目录 下创建一个SEQUENCE|EPHEMERAL类型的节点,例如“/election/n_”。在SEQUENCE标志下,ZooKeeper将自动地 为每一个ZooKeeper服务器分配一个比前一个分配的序号要大的序号。此时创建节点的ZooKeeper服务器中拥有最小序号编号的服务器将成为 Leader

在实际的操作中,还需要保障:当Leader服务器发生故障的时候,系统能够快速地选出下一个ZooKeeper服务器作为Leader。一个简 单的解决方案是,让所有的follower监视leader所对应的节点。当Leader发生故障时,Leader所对应的临时节点将会自动地被删除,此 操作将会触发所有监视Leader的服务器的watch。这样这些服务器将会收到Leader故障的消息,并进而进行下一次的Leader选举操作。但 是,这种操作将会导致从众效应的发生,尤其当集群中服务器众多并且带宽延迟比较大的时候,此种情况更为明显。

Zookeeper中,为了避免从众效应的发生,它是这样来实现的:每一个followerfollower集群中对应的比自己节点序号小一 号的节点(也就是所有序号比自己小的节点中的序号最大的节点)设置一个watch。只有当follower所设置的watch被触发的时候,它才进行 Leader选举操作,一般情况下它将成为集群中的下一个Leader。很明显,此Leader选举操作的速度是很快的。因为,每一次Leader选举几 乎只涉及单个follower的操作

2.Observer

      observer的行为在大多数情况下与follower完全一致, 但是他们不参加选举和投票, 而仅仅接受(observing)选举和投票的结果.

Zookeeper集群,选举机制

 

 

zookeeper选举机制

FastLeaderElection算法通过异步的通信方式来收集其它节点的选票,同时在分析选票时又根据投票者的当前状态来作不同的处理,以加快Leader的选举进程。    
    每个在zookeeper服务器启动先读取当前保存在磁盘的数据,zookeeper中的每份数据都有一个对应的id值,这个值是依次递增的;换言之,越新的数据,对应的ID值就越大。 
    在读取数据完毕之后,每个zookeeper服务器发送自己选举的leader,这个协议中包含了以下几部分的数据: 
1)、所选举leader的id(就是配置文件中写好的每个服务器的id) ,在初始阶段,每台服务器的这个值都是自己服务器的id,也就是它们都选举自己为leader。 
2)、服务器最大数据的id,这个值大的服务器,说明存放了更新的数据。 
3)、逻辑时钟的值,这个值从0开始递增,每次选举对应一个值,也就是说:如果在同一次选举中,那么这个值应该是一致的,逻辑时钟值越大,说明这一次选举leader的进程更新。 
4)、本机在当前选举过程中的状态,有以下几种:LOOKING,FOLLOWING,OBSERVING,LEADING 

    每台服务器将自己服务器的以上数据发送到集群中的其他服务器之后,同样的也需要接收来自其他服务器的数据,它将做以下的处理: 
A、如果所接收数据服务器的状态还是在选举阶段(LOOKING 状态),那么首先判断逻辑时钟值,又分为以下三种情况: 
a) 如果发送过来的逻辑时钟大于目前的逻辑时钟,那么说明这是更新的一次选举,此时需要更新一下本机的逻辑时钟值,代码如下: 

if (n.epoch > logicalclock) { logicalclock = n.epoch; recvset.clear(); if(totalOrderPredicate(n.leader, n.zxid,getInitId(), getInitLastLoggedZxid())) updateProposal(n.leader, n.zxid); else updateProposal(getInitId(),getInitLastLoggedZxid()); sendNotifications();


其中的totalOrderPredicate函数就是根据发送过来的封包中的leader id,数据id来与本机保存的相应数据进行判断的函数(首先看数据id,数据id大者胜出;其次再判断leader id,leader id大者胜出),返回true则调用updateProposal函数更新数据。 
b) 发送过来数据的逻辑时钟小于本机的逻辑时钟 
说明对方在一个相对较早的选举进程中,这里只需要将本机的数据广播出去 
c) 两边的逻辑时钟相同,此时也只是调用totalOrderPredicate函数判断是否需要更新本机的数据,将最新的选举结果广播出去 


B、如果所接收服务器不在选举状态,也就是在FOLLOWING或者LEADING状态 
a) 如果逻辑时钟相同,将该数据保存到recvset,如果所接收服务器宣称自己是leader,那么将判断是不是有半数以上的服务器选举它,如果是则设置选举状态退出选举过程 
如果逻辑时钟不相同,那么说明在另一个选举过程中已经有了选举结果,于是将该选举结果加入到outofelection集合中,再根 据outofelection来判断是否可以结束选举,如果可以也是保存逻辑时钟,设置选举状态,退出选举过程 

以一个简单的例子来说明整个选举的过程. 
假设有五台服务器组成的zookeeper集群,它们的id从1-5,同时它们都是最新启动的,也就是没有历史数据,在存放数据量这一点上,都是一样的.假设这些服务器依序启动,来看看会发生什么 

1) 服务器1启动,此时只有它一台服务器启动了,它发出去的报没有任何响应,所以它的选举状态一直是LOOKING状态  
2) 服务器2启动,它与最开始启动的服务器1进行通信,互相交换自己的选举结果,由于两者都没有历史数据,所以id值较大的服务器2胜出,但是由于没有达到超 过半数以上的服务器都同意选举它(这个例子中的半数以上是3),所以服务器1,2还是继续保持LOOKING状态.  
3) 服务器3启动,根据前面的理论分析,服务器3成为服务器1,2,3中的老大,而与上面不同的是,此时有三台服务器选举了它,所以它成为了这次选举的leader.  
4) 服务器4启动,根据前面的分析,理论上服务器4应该是服务器1,2,3,4中最大的,但是由于前面已经有半数以上的服务器选举了服务器3,所以它只能接收当小弟的命了.  
5) 服务器5启动,同4一样,当小弟

 

转载于:https://www.cnblogs.com/JimBo-Wang/p/6627133.html

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/284135.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

memcache的学习路线图

memcache学习材料//memcache自带的github 上的 wiki//席剑飞 Memcache(MC)系列 1~8系列评注: memcache系统写的最深的一博客,建议一读。http://blog.csdn.net/xifeijian/article/details/21994941//mysql与memcache的使用https://…

[转]钱岭:别担心“35岁危机”,要成为“老专家”

从清华大学到贝尔实验室,再到中国移动,作为“IT老人”,钱岭的技术人生几乎覆盖了20世纪90年代至今的信息产业革命。2007年开始,钱岭在中国移动经历了基础科研到产品落地,再到团队孵化;也经历了云计算从无到…

【GIS前沿】周成虎院士:GIS的大数据时代展望(PPT分享)

本文源自微信公众号:宋关福GIS笔记。版权归原作者及刊载媒体所有,如有侵权请立即与我们联系,我们将及时处理。更多GIS前言技术,请关注《GIS前言》专栏。 GIS的大数据时代展望

DataV:可视化大屏展示神器实战分享

由于公司年即将发布新的产品,传统意义上的PPT显得不太生动化,所以想采用具体化,可视化的数据大屏进行业务数据的事实展示,第一时间想到了来自于阿里云旗下的DataV,废话不多说,老司机开始发牌照!…

数据库性能系列之索引(中)

GOOD NIGHT前言上一篇中,我们已经了解到了索引的基本概念和一些用法。那索引为什么会提升查询的速度,以及索引究竟是怎么工作的呢?也许大家心里还是有一些迷茫,这一切,还要从索引背后的算法说起。GOOD NIGHT概述大家知…

微服务架构的设计原则和核心话题

目录 一、前言 二、微服务架构的设计原则 1.拆分足够微 2.轻量级通信 3.单一职责原则 4.领域驱动原则 三、微服务架构的核心话题 1.服务拆分 2.服务注册与发现 3.负载均衡 4.API网关 5.服务部署与发布 四、总结 一、前言 毫无疑问,微服务架构的设计原…

4.3.2 基于集合的操作

在SQL Server处理select命令时,会在内存中建立一个结构,以返回结果集。这个结构实质上是一个有行和列的二维数组,称为“游标(cursor)”。“游标”这个词是“CURrent set of Records(当前记录集)”的缩写。它表示从表或…

Golang GOPATH 包

2019独角兽企业重金招聘Python工程师标准>>> Golang GOPATH & 包的定义 & 包的导入 GOPATH 设置 go 命令依赖一个重要的环境变量:$GOPATH 可以在 .zshrc 配置文件中加上一行这样的配置, export GOPATH/Users/flyme/mygo Go从1.1版本到…

PPK大疆无人机应用教程

文章目录 一、新建项目二、导入数据三、解算过程四、结果导出一、新建项目 新建工程,设置项目名称,保存位置,控制等级,坐标系统(坐标系统选择高斯克吕格,中央子午线根据实际数据所在位置进行选择) 二、导入数据 选择大疆数据,找到对应的文件夹 数据有:图片,EVENT.b…

Eclipse Add generated serial version ID报错解决方案

为什么80%的码农都做不了架构师?>>> 问题: The following problem occurred:Could not find class file.Make sure the file is compilable 解决方案: 1、右键项目 -> Java Build Path -> Source 在Sourcd folders on bui…

开启线程的方式

1、实现Runnable接口 1 package test;2 3 4 5 public class ThreadTest implements Runnable{6 public void tt(){7 Thread t new Thread(this);8 t.start();9 } 10 11 Override 12 public void run() { 13 while(true){ 14 …

C# WPF设备监控软件(经典)-上篇

01—前言应老东家也是老同学的需求,开发了此设备监控软件。主要是为了应对测试设备长时间不上传测试数据未能及时发现的问题,测试数据一般在每台设备都有个固定的临时存放目录,测试数据不更新时,此文件夹便不再更新。需求相对比较…

[转]微服务的4个设计原则和19个解决方案

目录 一、微服务架构演进过程 二、微服务架构的好处 三、微服务应用4个设计原则 1.AKF拆分原则 2.前后端分离 3.无状态服务 4.Restful通信风格 四、微服务架构带来的问题 五、微服务平台的19个落地实践 1.企业IT建设的三大基础环境 2.微服务应用平台总体架构 3.微服…

时间处理总结(二)oracle

不断总结中................. 1.等于land.djsjto_date(2016/7/26,yyyy-MM-dd)2.大于等于land.djsj>to_date(2016/7/26,yyyy-MM-dd)3.小于等于land.djsj<to_date(2016/7/26,yyyy-MM-dd)4.区间land.djsj>to_date(2016/7/26,yyyy-MM-dd) and land.djsj<to_date(2016/7…

【GlobalMapper精品教程】033:影像地图羽化方式详解

在Globalmapper中,可以很方便的对影响进行多种羽化值设置。 文章目录 1. 不要羽化此图层2. 沿一个或多个边缘羽化3. 羽化到有效数据的多边形覆盖4. 在当前选定的多边形内羽化5. 裁剪到选定的边界,而不是羽化6. 在多边形外部羽化,而不是内部加载配套案例数据包中的data033.ra…

基于WPF重复造轮子,写一款数据库文档管理工具(一)

项目背景公司业务历史悠久且复杂&#xff0c;数据库的表更是多而繁杂&#xff0c;每次基于老业务做功能开发都需要去翻以前的表和业务代码。需要理解旧的表的用途以及包含的字段的含义&#xff0c;表少还好说&#xff0c;但是表一多这就很浪费时间&#xff0c;而且留下来的文档…

[转]GitBook使用教程收藏

GitBook使用教程 最简单的方式就是使用GitBook编辑器&#xff0c;没有什么难度&#xff0c;后面的教程主要针对命令行的方式 PS&#xff1a;GitBook的book页面默认没有download按钮的 需要到设置中打开&#xff0c;打开后再次publish生效 同步GitHub 更新失败&#xff0c;无法…

二 面向对象三大特性

一 继承与派生 一、继承定义 二、继承与抽象的关系 三、继承与重用性 四、派生 五、组合与重用性 六、接口与归一化设计 七、抽象类 八、继承实现的原理 九、子类中调用父类的方法 二 多态与多态性 一、多态 二、多态性 三 封装 一、封装定义 二、特性(property) 三、封装与扩展…

CSS3新属性

边框&#xff1a; border-radius 用于创建圆角 div { border:2px solid; border-radius:25px; -moz-border-radius:25px; /* Old Firefox */ } box-shadow 用于向方框添加阴影 div { box-shadow: 10px 10px 5px #888888; } border-image 使用图片来创建边框 div { border-image…

Android实用笔记——使用Spinner实现下拉列表

2019独角兽企业重金招聘Python工程师标准>>> 1、编辑activity_main.xml <?xml version"1.0" encoding"utf-8"?> <LinearLayout xmlns:android"http://schemas.android.com/apk/res/android"android:layout_width"mat…