Zookeeper 本地模拟伪集群环境(一 leader 多 follower)
Author QiuRiMangCao 秋日芒草
ZooKeeper介绍
ZooKeeper是一个分布式开源框架,提供了协调分布式应用的基本服务,
它向外部应用暴露一组通用服务——分布式同步(Distributed Synchronization)、
命名服务(Naming Service)、集群维护(Group Maintenance)等,
简化分布式应用协调及其管理的难度,提供高性能的分布式服务。
ZooKeeper本身可以以Standalone模式安装运行,不过它的长处在于通过分布式
ZooKeeper集群(一个Leader,多个Follower),基于一定的策略来
保证ZooKeeper集群的稳定性和可用性,从而实现分布式应用的可靠性。
在zk安装目录下的conf文件下创建一个my_cluster文件夹,并cp三份zk默认配置文件zoo_01.cfg zoo_02.cfg zoo_03.cfg
[root@localhost zookeeper-3.3.6]# cd conf/
[root@localhost conf]# ls
configuration.xsl log4j.properties my_cluster zoo.cfg zoo_sample.cfg
[root@localhost conf]# cd my_cluster/
[root@localhost my_cluster]# ls
zoo_01.cfg zoo_02.cfg zoo_03.cfg
zoo_01.cfg 的配置如下
[root@localhost my_cluster]# cat ./zoo_01.cfg
# The number of milliseconds of each tick
tickTime=2000
# The number of ticks that the initial
# synchronization phase can take
initLimit=10
# The number of ticks that can pass between
# sending a request and getting an acknowledgement
syncLimit=5
# the directory where the snapshot is stored.
dataDir=/my_package/data/zk_data01
# the port at which the clients will connect
clientPort=2181
# cluster config
server.1=localhost:2887:3887
server.2=localhost:2888:3888
server.3=localhost:2889:3889
service配置讲解
server.A=B:C:D:
A 是一个数字,表示这个是第几号服务器;
B 是这个服务器的 ip 地址;
C 表示的是这个服务器与集群中的 Leader 服务器交换信息的端口;
D 表示的是万一集群中的 Leader 服务器挂了,需要一个端口来重新进行选举,
选出一个新的 Leader,而这个端口就是用来执行选举时服务器相互通信的端口。
如果是伪集群的配置方式,由于 B 都是一样,所以不同的 Zookeeper 实例通信端口号不能一样,
所以要给它们分配不同的端口号。
- tickTime:zookeeper中使用的基本时间单位, 毫秒值。
- initLimit:这个配置项是用来配置 Zookeeper 接受客户端(这里所说的客户端不是用户连接 Zookeeper 服务器的客户端,而是 Zookeeper 服务器集群中连接到 Leader 的 Follower 服务器)初始化连接时最长能忍受多少个 tickTime 时间间隔数。这里设置为5表名最长容忍时间为 5 * 2000 = 10 秒。
- syncLimit:这个配置标识 Leader 与 Follower 之间发送消息,请求和应答时间长度,最长不能超过多少个 tickTime 的时间长度,总的时间长度就是 2 * 2000 = 4 秒。
- dataDir 和 dataLogDir 看配置就知道干吗的了,不用解释。
- clientPort:监听client连接的端口号,这里说的client就是连接到Zookeeper的代码程序。
- server.{myid}={ip}:{leader服务器交换信息的端口}:{当leader服务器挂了后, 选举leader的端口}
- maxClientCnxns:对于一个客户端的连接数限制,默认是60,这在大部分时候是足够了。但是在我们实际使用中发现,在测试环境经常超过这个数,经过调查发现有的团队将几十个应用全部部署到一台机器上,以方便测试,于是这个数字就超过了。
zoo_02.cfg 的配置如下
[root@localhost my_cluster]# cat zoo_02.cfg
# The number of milliseconds of each tick
tickTime=2000
# The number of ticks that the initial
# synchronization phase can take
initLimit=10
# The number of ticks that can pass between
# sending a request and getting an acknowledgement
syncLimit=5
# the directory where the snapshot is stored.
dataDir=/my_package/data/zk_data02
# the port at which the clients will connect
clientPort=2182
# cluster config
server.1=localhost:2887:3887
server.2=localhost:2888:3888
server.3=localhost:2889:3889
zoo_03.cfg 的配置如下
[root@localhost my_cluster]# cat zoo_03.cfg
# The number of milliseconds of each tick
tickTime=2000
# The number of ticks that the initial
# synchronization phase can take
initLimit=10
# The number of ticks that can pass between
# sending a request and getting an acknowledgement
syncLimit=5
# the directory where the snapshot is stored.
dataDir=/my_package/data/zk_data03
# the port at which the clients will connect
clientPort=2183
# cluster config
server.1=localhost:2887:3887
server.2=localhost:2888:3888
server.3=localhost:2889:3889
在如上cfg配置文件配置的dataDir=/my_package/data/zk_data01来指定zk数据存放路径
[root@localhost data]# pwd
/my_package/data
[root@localhost data]# ls
zk_data01 zk_data02 zk_data03
并数据存放路径下新建一个myid文件,分别是1,2,3,对应cfg中的配置文件中的server.1 ..
[root@localhost zk_data01]# ls
myid
指定配置文件启动zk服务于
bin/zkServer.sh start ./conf/zoo_01.cfg
bin/zkServer.sh start ./conf/zoo_02.cfg
bin/zkServer.sh start ./conf/zoo_03.cfg
获取每一台zk的Mode信息(leader,follower)leader:为领导者 follower:追随者
一个时候只有一台leader提供对外服务
[root@localhost bin]# ./zkServer.sh status ../conf/my_cluster/zoo_01.cfg
JMX enabled by default
Using config:../conf/my_cluster/zoo_01.cfg
Using config: ../conf/my_cluster/zoo_01.cfg
Mode: follower
[root@localhost bin]# ./zkServer.sh status ../conf/my_cluster/zoo_02.cfg
JMX enabled by default
Using config:../conf/my_cluster/zoo_02.cfg
Using config: ../conf/my_cluster/zoo_02.cfg
Mode: leader
[root@localhost bin]# ./zkServer.sh status ../conf/my_cluster/zoo_03.cfg
JMX enabled by default
Using config:../conf/my_cluster/zoo_03.cfg
Using config: ../conf/my_cluster/zoo_03.cfg
Mode: follower
停掉zoo_02这台服务,整个集群还有二台zk可以对外提供服务
[root@localhost bin]# ./zkServer.sh stop ../conf/my_cluster/zoo_02.cfg
再停掉一台,整个集群不可用超过一半(因为只有3台机器,坏了二台了),整个集群不可用
[root@localhost bin]# ./zkServer.sh stop ../conf/my_cluster/zoo_01.cfg
此时zk的服务状态
[root@localhost bin]# ./zkServer.sh status ../conf/my_cluster/zoo_01.cfg
JMX enabled by default
Using config:../conf/my_cluster/zoo_01.cfg
Using config: ../conf/my_cluster/zoo_01.cfg
Error contacting service. It is probably not running.
[root@localhost bin]# ./zkServer.sh status ../conf/my_cluster/zoo_02.cfg
JMX enabled by default
Using config:../conf/my_cluster/zoo_02.cfg
Using config: ../conf/my_cluster/zoo_02.cfg
Error contacting service. It is probably not running.
[root@localhost bin]# ./zkServer.sh status ../conf/my_cluster/zoo_03.cfg
JMX enabled by default
Using config:../conf/my_cluster/zoo_03.cfg
Using config: ../conf/my_cluster/zoo_03.cfg
Error contacting service. It is probably not running.
总结:伪集群能模拟出服务挂掉后的选举情况,但对于客户端不是无感的,客户端已有的连接会断掉,会给客户端提示拒绝连接。如下是挂掉的服务zk在客户端出现的连接拒绝异常:
2017-10-20 13:38:49,660 - INFO [main-SendThread(localhost:2182):ClientCnxn$SendThread@1058] - Opening socket connection to server localhost/0:0:0:0:0:0:0:1:2182
2017-10-20 13:38:49,662 - WARN [main-SendThread(localhost:2182):ClientCnxn$SendThread@1185] - Session 0x25f383c0da90000 for server null, unexpected error, closing socket connection and attempting reconnect
java.net.ConnectException: 拒绝连接
at sun.nio.ch.SocketChannelImpl.checkConnect(Native Method)
at sun.nio.ch.SocketChannelImpl.finishConnect(SocketChannelImpl.java:717)
at org.apache.zookeeper.ClientCnxn$SendThread.run(ClientCnxn.java:1143)
2017-10-20 13:38:51,324 - INFO [main-SendThread(localhost:2182):ClientCnxn$SendThread@1058] - Opening socket connection to serve
参考博客:http://www.cnblogs.com/rwxwsblog/p/5806075.html
http://blog.csdn.net/catoop/article/details/50848555