使用小记:Zookeeper中动态改变节点的功能
Zookeeper 3.5+提供了reconfig功能实现动态配置节点,官方的说明是,“你再也不需要进行全部节点重启”就可以应用所有的修改:
http://zookeeper.apache.org/doc/r3.5.4-beta/zookeeperReconfig.html
我们不妨按照官方的说明尝试一下。
根据文档,我们先配置一个3节点集群好了,配置文件内容如下:
zoo1.cfg
reconfigEnabled=true
standaloneEnabled=false
tickTime=2000
dataDir=/tmp/zkcluster/zk1
initLimit=5
syncLimit=2
clientPort=2791
server.1=127.0.0.1:2780:2783:participant;2791
server.2=127.0.0.1:2781:2784:participant;2792
server.3=127.0.0.1:2782:2785:participant;2793
zoo2.cfg
reconfigEnabled=true
standaloneEnabled=false
tickTime=2000
dataDir=/tmp/zkcluster/zk2
initLimit=5
syncLimit=2
clientPort=2792
server.1=127.0.0.1:2780:2783:participant;2791
server.2=127.0.0.1:2781:2784:participant;2792
server.3=127.0.0.1:2782:2785:participant;2793
zoo3.cfg
reconfigEnabled=true
standaloneEnabled=false
tickTime=2000
dataDir=/tmp/zkcluster/zk3
initLimit=5
syncLimit=2
clientPort=2793
server.1=127.0.0.1:2780:2783:participant;2791
server.2=127.0.0.1:2781:2784:participant;2792
server.3=127.0.0.1:2782:2785:participant;2793
其实这三个配置文件基本相同,差别就是dataDir和clientPort不同。
请注意如下几点:
1. reconfigEnabled=true,这个配置是用来实现动态配置的,一定要设置,否则集群启动后会无法修改现有配置
2. standaloneEnabled=false,根据官方文档:
http://zookeeper.apache.org/doc/r3.5.4-beta/zookeeperReconfig.html#sc_reconfig_standaloneEnabled
的"The standaloneEnabled flag"章节,文中提到的:
Prior to 3.5.0, one could run ZooKeeper in Standalone mode or in a Distributed mode. These are separate implementation stacks, and switching between them during run time is not possible. By default (for backward compatibility) standaloneEnabled is set to true. The consequence of using this default is that if started with a single server the ensemble will not be allowed to grow, and if started with more than one server it will not be allowed to shrink to contain fewer than two participants. Setting the flag to false instructs the system to run the Distributed software stack even if there is only a single participant in the ensemble. To achieve this the (static) configuration file should contain: standaloneEnabled=false
因为Standalone和Ensemble模式使用的是不同的实现栈,为了让我们的集群能够动态增加和减少节点,并且集群节点能够少于2,最好使用Ensemble模式。
3. clientPort=2793, 官方文档不建议使用这个参数,但是我实在不知道如何配置连接用的端口,所以保留了这个参数
4. dataDir, 请为每个节点单独配置一个数据目录,且里面建立一个名为“myid”的文件,内容为本节点的id(例如dataDir=/tmp/zkcluster/zk1的节点,在此目录创建myid文件,内容为1)。这个目录会存放集群数据的快照。
当我们设置好上述参数后,即可启动节点:
上图中,我写了个脚本能够只要输入节点的编号即可启动,实际上执行时,请使用:
zkServer.sh start /dir/to/zookeeper/conf/zooN.cfg
启动
此时我们连上任何一个节点,可以看到集群已经启动了:
zkCli.sh -server 127.0.0.1:2791
连上集群后使用config命令检查节点:
至此为止都是基本操作,接下来到达最重要的部分:动态配置集群以实现增加或者减少节点
首先我们以下述配置文件再启动一个节点:
reconfigEnabled=true
standaloneEnabled=false
tickTime=2000
dataDir=/tmp/zkcluster/zk4
initLimit=5
syncLimit=2
clientPort=2794
server.1=127.0.0.1:2780:2783:participant;2791
server.4=127.0.0.1:2801:2802:participant;2794
配置在前面的章节已经解释过了,但是配置节点时只设置了两个,这一点可能会令人迷惑,在这里说明一下:大家如果参考文档,会发现3.5+版本会自动把配置文件变为动态配置文件,静态的部分还是放在原来的zooN.cfg当中,动态的部分放到了zooN.cfg.dynamic.xxx当中了,而且集群的配置文件在绝大多数时间中都是一致的,只有在重新配置的时候会经历短暂的不一致,利用这一特性,让新加入节点连接到集群上,然后从集群同步配置过来即可。
启动这个节点后,连接上这个节点观察集群:
大家可以看到,这个节点实际上是连接到集群的,但是从集群上同步的配置却不包含本节点。
注意:前面提到过自动同步配置的机制,此时本节点(节点4)会将集群配置同步到本地,如果此时重启节点,节点将没有办法再次被启动,因为集群中不包含本节点。
现在连接到任何一个集群内节点(1,2,或者3),使用下述命令添加节点:
reconfig -add server.4=127.0.0.1:2801:2802:participant;2794
然后就。。。。。失败了:
搜索一下Authentication is not valid,可以知道是因为服务器默认没有/zookeeper/config的写入权限导致的,此时需要添加写入权限:
1. 先进入zookeeper的安装目录,然后执行下述命令产生认证使用的摘要信息:
java -cp ./lib/*:./* org.apache.zookeeper.server.auth.DigestAuthenticationProvider su:passwd
说明下,这条命令实际上在执行zookeeper的org.apache.zookeeper.server.auth.DigestAuthenticationProvider功能,
使用用户名:su
和密码:passwd
产生认证参数,执行完毕后程序返回:
su:passwd->su:gACzJ4L2A0F2ygTno5HQnfabuik=
2. 修改zkServer.sh,添加下述命令行:
SERVER_JVMFLAGS="-Dzookeeper.DigestAuthenticationProvider.superDigest=su:gACzJ4L2A0F2ygTno5HQnfabuik="
其中红色部分是上一步(1)产生的摘要信息。
然后重启集群中的一个节点
3. 连接步骤2中重启的节点,执行下述命令:
addauth digest su:passwd
reconfig -add server.4=127.0.0.1:2801:2802:participant;2794
结果如图:
此时我们连接到第四个节点,然后通过config检查:
发现第四个节点确实已经在集群中了,图中我还在第四个节点get了一下/k的值,这个值是在第一个节点设置的,可以看到,数据也同步过来了。
终于用上了zookeeper的动态配置功能,再也不用一个一个重启实例来添加集群节点了
最后,关于zookeeper集群的几点思考:
1. 在整个集群中,保留几个节点作为核心集群,当要添加、删除节点时,从这些节点进行,这样就不需要为所有的节点都提供/zookeeper/config的写入权限,在生产环境中要是每个节点都获取了写入权限,很有可能导致非专职运维的成员能够修改集群信息。当然,最重要的还是密码的保护,要是密码被非运维人员知道了,同时他也知道核心节点的地址,一样可以修改集群配置。
2. 关于集群节点数量的问题,上面的例子中,我们向3节点的集群增加了一个节点,这只是一个说明动态配置zookeeper的例子,实际使用时集群节点数量最好为奇数,因为zookeeper是基于大多数节点可用时集群可用的,也就是说,当有5个节点时,可以容忍2个节点的失效,而当拥有4个节点时,只能容忍一个节点失效,和拥有3个节点效果一样。
zookeeper的官方文档中,有两处描述了这个问题,第一处是:
http://zookeeper.apache.org/doc/r3.5.4-beta/zookeeperStarted.html#sc_RunningReplicatedZooKeeper
“Running Replicated ZooKeeper”章节的Note部分,明确说明了集群要使用奇数个节点,但是只是说了两个节点系统没有一个节点系统稳定
第二个就是(个人觉得这一段最明确):
http://zookeeper.apache.org/doc/r3.1.2/zookeeperAdmin.html#sc_designing
“Designing a ZooKeeper Deployment”章节的“Cross Machine Requirements”中,有集群中节点数量的计算公式:
2xF+1
其中F是集群容忍失效机器的数目,通过这个公式计算,3个节点的集群和4个节点的集群都只能容忍1个节点的失效
3. 关于动态向集群添加节点
其实有三种方式向集群添加节点(再次搬出官方文档):
http://zookeeper.apache.org/doc/r3.5.4-beta/zookeeperReconfig.html#sc_reconfig_modifying
请看到“Adding servers”部分:
1. 通过配置文件将要添加的节点当作Observer加入集群(可以添加多个节点),然后再在系统中重新配置为Participant
2. 通过配置文件将要添加的节点当作Participant加入集群,每个节点的配置文件只能添加集群节点和自己,否则新加入的节点可能形成一个集群,导致发生脑裂,请参考下面的“Warning”部分
3. 仅将Leader节点和自己加入配置文件,然后通过reconfig将自身加入集群(本实例中使用的方法),这种方法有两个前提条件:
a. 配置文件中只能出现自身节点和Leader节点
b. 如果添加节点的过程中Leader挂掉,此时自身的配置已经有问题了,需要下线本节点重新配置再加入
实际生产时,使用1是最可靠的。
使用小记:Zookeeper中动态改变节点的功能的更多相关文章
- 代码中动态改变布局属性RelativeLayout.LayoutParams.addRule()
我们知道,在 RelativeLayout 布局中有很多特殊的属性,通常在载入布局之前,在相关的xml文件中进行静态设置即可. 但是,在有些情况下,我们需要动态设置布局的属性,在不同的条件下设置不同的 ...
- Android中动态改变控件的大小的一种方法
在Android中有时候我们需要动态改变控件的大小.有几种办法可以实现 一是在onMeasure中修改尺寸,二是在onLayout中修改位置和尺寸.这个是可以进行位置修改的,onMeasure不行. ...
- WPF 中动态改变控件模板
在某些项目中,可能需要动态的改变控件的模板,例如软件中可以选择不同的主题,在不同的主题下软件界面.控件的样式都会有所不同,这时即可通过改变控件模板的方式实现期望的功能. 基本方法是当用户点击切换主题按 ...
- CKEDITOR 3.4.2中 按钮事件中 动态改变图标和title 获取按钮
this.uiItems[0].className="cke_button_hui_position_type";this.uiItems[0].title="zhang ...
- ThinkPhp 中Action控制器中动态改变自动完成规则(使用setProperty)
Common.php中定义的方法 在更新数据时动态规则中 "完成时间" 必须设定为2
- 给div中动态添加节点并设置样式
前端IOS今天需要动态的在图片前面添加一个按钮 主要是在使用 bt.setAttribute("class","aaa"); 可以对创建的节点使用setAttr ...
- 【转载】在程序中动态改变static text控件的caption值
方法1,给STATIC控件取个名字叫IDC_STATICTITLE 然后在ClassWizard中设定一个控件变量给它叫m_statictitle 然后用m_statictitle.SetWindow ...
- hadoop集群中动态添加节点
集群的性能问题需要增加服务器节点以提高整体性能 https://www.cnblogs.com/fefjay/p/6048269.html hadoop集群之间hdfs文件复制 https://www ...
- Android中动态改变Listview中字体的颜色
效果如下: 账目显示用的是Listview,要实现的功能为使其根据所在Item是“收入”还是“支出”来把数字设置成绿色或红色 方法是自定义适配器,并重写其中getView()函数,实现如下: //自定 ...
随机推荐
- [源码解析] 并行分布式框架 Celery 之 worker 启动 (1)
[源码解析] 并行分布式框架 Celery 之 worker 启动 (1) 目录 [源码解析] 并行分布式框架 Celery 之 worker 启动 (1) 0x00 摘要 0x01 Celery的架 ...
- Python基础之数据类型详解(2)
今天继续昨天的python基本数据类型详解,按照上一篇博文的格式,接下来讲解列表.元组.字典以及集合. 列表 1.用途按位置存放多个值2.定义在[]内用逗号分割开多个任意类型的元素 # 定义列表 # ...
- 生产中常用的du命令
1. 介绍 du是用来查看文件或目录所占用磁盘空间的大小 du [-abcDhHklmsSx] [-L <符号连接>][-X <文件>][--block-size][--exc ...
- BUAA_2021_SE_Case_Analysis
案例分析作业 项目 内容 这个作业属于哪个课程 2021春季计算机学院软件工程(罗杰 任健) 这个作业的要求在哪里 案例分析作业 我在这个课程的目标是 通过课程学习,完成第一个可以称之为"软 ...
- 软工案例分析作业-CSDN
项目 内容 这个作业属于哪个课程 2021春季计算机学院软件工程(罗杰 任健) 这个作业的要求在哪里 案例分析作业要求 我在这个课程的目标是 提升软件开发能力与团队意识 这个作业在哪个具体方面帮助我实 ...
- 腾讯高级工程师带你完整体验Node.js开发实战
Node.js拥有广大的 JavaScript程序员基础并且完全开源,它被广泛地用在 Web服务.开发工作流.客户端应用等诸多领域.在 Web 服务开发这个领域,业界对 Node.js 的接受程度最高 ...
- Math类的random()方法
Math类的random()方法 Math类的random()方法可以生成大于等于0.0.小于1.0的double型随机数. Math.random()方法语句基础上处理可获得多种类型.或任意范围的随 ...
- 【项目】手写FTP服务器-C++实现FTP服务器
X_FTP_server 手写FTP服务器-C++实现FTP服务器 项目Gitee链接:https://gitee.com/hsby/ftp_Server 简介 一个基于libevent的高并发FTP ...
- ElasticSearch-03-远行、停止
在Windows下执行elasticsearch.bat 在Linux下运行./elasticsearch 指定集群名称和节点名称: ./elasticsearch --cluster.name my ...
- Mediapipe 在RK3399PRO上的初探(二)(自定义Calculator)
PS:要转载请注明出处,本人版权所有. PS: 这个只是基于<我自己>的理解, 如果和你的原则及想法相冲突,请谅解,勿喷. 前置说明 本文作为本人csdn blog的主站的备份.(Bl ...