版本声明
Zookeeper
版本3.4.6
配置文件详解
-
单击配置
参数名 默认值 描述 clientPort
无默认值,必须配置 服务的监听端口,一般设置2181,集群中不同机器的端口可以不同 dataDir
无默认值,必须配置 用于存放内存数据快照的文件夹,同时集群的myid文件也存在这个文件夹里 dataLogDir
默认与dataDir目录相同 事务日志写入目录,尽量不要与dataDir同一个目录,甚至不要在一块磁盘上,避免事务日志与快照数据对磁盘的竞争 tickTime
2000 Zookeeper的时间单元。Zookeeper中所有时间都是以这个时间单元的整数倍去配置的。例如,session的最小超时时间是2*tickTime。(单位:毫秒) globalOutstandingLimit 1000 最大请求堆积数。默认是1000。Zookeeper运行过程中,尽管Server没有空闲来处理更多的客户端请求了,但是还是允许客户端将请求提交到服务器上来,以提高吞吐性能。当然,为了防止Server内存溢出,这个请求堆积数还是需要限制下的。 preAllocSize 65535KB 预先开辟磁盘空间,用于后续写入事务日志。默认是64M,每个事务日志大小就是64M。如果ZK的快照频率较大的话,建议适当减小这个参数。 snapCount 100,000 每进行snapCount次事务日志输出后,触发一次快照, 此时,Zookeeper会生成一个snapshot.文件,同时创建一个新的事务日志文件log.。默认是100,000. traceFile 用于记录所有请求的log,一般调试过程中可以使用,但是生产环境不建议使用,会严重影响性能。 maxClientCnxns
60 单个客户端与单个服务器之间的最大并发连接数,默认值是60(3.4.0版本开始),设置为0是不加限制 clientPortAddress 对于多网卡的机器,可以为每个IP指定不同的监听端口。默认情况是所有IP都监听 clientPort 指定的端口 minSessionTimeout/maxSessionTimeout Session超时时间限制,如果客户端设置的超时时间不在这个范围,那么会被强制设置为最大或最小时间。默认的Session超时时间是在2 * tickTime ~ 20 * tickTime 这个范围 fsync.warningthresholdms 10000 事务日志输出时,如果调用fsync方法超过指定的超时时间,那么会在日志中输出警告信息。默认是1000ms。 autopurge.snapRetainCount 参数指定了需要保留的事务日志和快照文件的数目。默认是保留3个。和autopurge.purgeInterval搭配使用 autopurge.purgeInterval 在3.4.0及之后版本,Zookeeper提供了自动清理事务日志和快照文件的功能,这个参数指定了清理频率,单位是小时,需要配置一个1或更大的整数,默认是0,表示不开启自动清理功能 syncEnabled true Observer写入日志和生成快照,这样可以减少Observer的恢复时间。默认为true。 -
集群主要选项
参数名 默认值 描述 initLimit 10 表示tickTime值的多少倍,该参数用于配置Leader服务器等待Follower启动,并完成数据同步的时间。Follower服务器在启动过程中,会与Leader建立连接并完成对数据的同步,从而确定自己对外提供服务的起始状态。Leader服务器允许Follower在initLimit*tickTime时间内完成这个工作。如果同步的数据量很大,可以把这个值设置的大一些 leaderServes yes 默认情况下,Leader是会接受客户端连接,并提供正常的读写服务。但是,如果你想让Leader专注于集群中机器的协调,那么可以将这个参数设置为 no,这样一来,会大大提高写操作的性能。一般机器数比较多的情况下可以设置为no,让Leader不接受客户端的连接。默认为yes syncLimit 5 表示tickTime值的5倍,用于配置Leader服务器和Follower之间进行心跳检测的最大延迟时间。在zk集群运行过程中,Leader服务器会与所有的Follower服务器进行心跳检测来确定服务器是否存活,如果Leader服务器在syncLimit* tickTime时间内无法获取到Follower的心跳检测响应,那么Leader就会认为该Follower已经脱离了和自己的同步 cnxTimeout 5000ms Leader选举过程各服务器之间进行TCP连接创建的超时时间 standaloneEnabled 当设置为false时,服务器在复制模式下启动
JMX
-
有时我们不希望在服务器之间配置ssh,或者管理各种密码公钥,但是又需要管控
Zookeeper
,此时可以开启JMX
功能 -
Zookeeper
默认开启了JMX
功能,但是却仅限本地连接,无法通过远程连接。可以修改zkServer.sh
,找到如下ZOOMAIN
配置
ZOOMAIN="-Dcom.sun.management.jmxremote -Dcom.sun.management.jmxremote.local.only=false -Djava.rmi.server.hostname=0.0.0.0 -Dcom.sun.management.jmxremote.port=10999 -Dcom.sun.management.jmxremote.ssl=true -Dcom.sun.management.jmxremote.authenticate=true -Dcom.sun.management.jmxremote.access.file=/root/jmx/jmxremote.access -Dcom.sun.management.jmxremote.password.file=/root/jmx/jmxremote.password -Dzookeeper.jmx.log4j.disable=true org.apache.zookeeper.server.quorum.QuorumPeerMain"
-
新建两个文件
/root/jmx/jmxremote.access
(访问用户角色和相关联的权限信息)和/root/jmxjmxremote.password
(指定每个角色的密码)。这两个文件的设置可以参考$JAVA_HOME/jre/lib/management
里的模板文件-
jmxremote.access 文件内容
monitorRole readonly controlRole readwrite \ create javax.management.monitor.*,javax.management.timer.* \ unregister
-
jmxremote.password文件内容
monitorRole 123456 controlRole abcdefg
-
-
ZooKeeper MBean Reference
:http://zookeeper.apache.org/doc/r3.4.6/zookeeperJMX.html
集群高可用
- 一个
Zookeeper
集群入股要对外提供可用的服务,那么集群中必须要有过半的机器正常工作并且彼此之间能够正常通信。基于这点,如果想要搭建一个能够允许N台机器宕机的集群,那么就要部署一个由2N+1台服务器构成的集群。从这个公式来看,一个由5台机器构成的集群和一个由6台机器构成的集群容灾能力是一样的,所以Zookeeper
集群通常设计部署成奇数台服务器 Zookeeper
基于过半的设计原则:在运行期间,集群中至少有过半的机器保存了最新的数据,整个集群就能够对外提供服务。从这点来看Zookeeper
集群本身就解决了单点问题。- 三机房容灾部署方案
- 前置条件,设集群总机器数为N,三个机房部署的
Zookeeper
服务器数量分别为N1
,N2
,N3
, - 计算N1:
N1=(N-1)/2
向下取整。如果N为7或者8,则N1=3 - 计算N2: N2的取值范围为
1~(N-N1)/2
- 计算N3,同时确定N2:
N3=N-N1-N2
并且N3<N1+N2
- 假设N=7,则最终部署方案为(N1=3,N2=1,N3=3) 和(N1=3,N2=2,N3=2)。这样就保证了任意一个机房宕机,剩下两个机房的机器总数一定是过半的。
- 前置条件,设集群总机器数为N,三个机房部署的
- 双机房容灾部署方案
- 理论上没有好的办法,因为无论哪个机房发生问题,都可能使得
Zookeeper
集群中可用的机器无法超过半数。 - 尽量在主要机房部署更多的机器,比如N=7,N1=4(主机房),N2=3
- 理论上没有好的办法,因为无论哪个机房发生问题,都可能使得
水平扩容
Zookeeper
在水平扩容方面做的不是很好(一般情况下集群数量也不能太多(3~5个实例即可),所以这个也不是什么问题),需要进行整个集群的重启(因为集群的配置文件zoo.cfg要修改)。重启有两种方式:集群整体全部重启
:重启过程中,所有客户端都无法连接上集群,重启完成之后,客户端会自动连接上————在整体重启期间花费的时间将不计入Sesssion
超时(会话超时)时间的计算。对于Zookeeper
不是核心组件的应用而言,可以选择这种方式逐台机器重启
:每次仅仅重启集群中的一台机器,然后逐台对整个集群中的机器进行重启操作
磁盘管理
Zookeeper
对于磁盘的依赖非常严重,所有数据状态的变量都会以事务日志的形式写入磁盘,并且只有当集群中过半的服务器都记录了该事务日志后,服务器才会给予客户端响应。Zookeeper
还会定时将内存数据库中的所有数据和所有客户端的会话信息记录进行快照,并保存在磁盘上的数据快照文件中去。所以磁盘的I/O性能直接制约Zookeeper
每个更新操作的处理速度。- 为了尽量减少
Zookeeper
在读写磁盘上的性能损失- 使用单独的磁盘作为事务日志的输出目录。事务日志的写性能对
Zookeeper
处理客户端请求,尤其是更新操作的处理性能影响很大。Zookeeper
的事务日志输出是一个顺序写文件的过程,本身的性能很高,尽量保证事务日志与快照数据分别配置在两块单独挂载的磁盘上,避免对事务日志与快照数据对磁盘的竞争。 - 尽量避免内存与磁盘空间的swap。如果希望
Zookeeper
能够提供完全实时的服务,就不能出现内存与磁盘空间的swap现象。因此在分配JVM堆大小的时候一定要非常小心
- 使用单独的磁盘作为事务日志的输出目录。事务日志的写性能对