ZooKeeper 教程

ZooKeeper 使用

ZooKeeper 高级教程

ZooKeeper 笔记

ZooKeeper 部署与运行


ZooKeeper 源码是由 Java 编写的,所以 ZooKeeper 的部署需要 java 环境;ZooKeeper 的运行模式及部署主要分为 3 种,单机模式、伪集群模式、集群模式。

系统环境

对于大部分 Java 开源产品而言,在部署与运行之前,总是需要搭建一个合适的环境,通常包括操作系统和 Java 环境两方面。

操作系统

首先,你需要选择一个合适的操作系统。幸运的是,ZooKeeper 对于不同平台的支持都很好,在现在绝大多数主流的操作系统上都能够正常运行,例如 GNU/Linux、Sun Solaris、Win32 以及 MacOSX 等。需要注意的是,ZooKeeper 官方文档中特别强调,由于 FreeBSD 系统的 JVM 对 Java 的 NIO Selector 支持得不是很好,所以不建议在该系统上部署生产环境的 ZooKeeper 服务器。

Java 环境

ZooKeeper 使用 Java 语言编写,因此它的运行环境需要 Java 环境的支持,Java 环境安装参考,Java 环境安装

集群与单机

ZooKeeper 有两种运行模式:集群模式和单机模式。下面介绍的涉及部署与配置操作都是针对 GNU/Linux 系统的。

集群模式

现在,我们开始讲解如何使用三台机器来搭建一个 ZooKeeper 集群。首先,我们假设已经准备好三台互相联网的 Linux 机器,它们的 ip 地址分别为 ip1、ip2 和 ip3。

初次使用 ZooKeeper,需要将%ZK_HOME%/conf 目录下的 zoo_sample.conf 文件重命名为 zoo.conf,并且按照如下代码进行简单配置即可:

tickTime=2000

# 目录路径
dataDir=/var/lib/zookeeper/data1

# 对外提供的端口
clientPort=2181
initLimit=10
syncLimit=5

#cluster conf
server.1=ip1:2887:3887
server.2=ip2:2888:3888
server.3=ip3:2889:3889

在集群模式下,集群中的每台机器都需要感知到整个集群是由哪几台机器组成的,在配置文件中,可以按照这样的格式进行配置,每一行都代表一个机器配置:

server.id=host:port:port

其中,id 被称为 Server ID,用来标识该机器在集群中的机器序号。同时,在每台 ZooKeeper 机器上,我们都需要在数据目录(即 dataDir 参数指定的那个目录)下创建一个 myid 文件,该文件只有一行内容,并且是一个数字,即对应于每台机器的 Server ID 数字。

在 ZooKeeper 的设计中,集群中所有机器上 zoo.conf 文件的内容都应该是一致的。因此最好使用 SVN 或是 GIT 把此文件管理起来,确保每个机器都能共享到一份相同的配置。

上面也提到了,myid 文件中只有一个数字,即一个 Server ID。例如,server.1 的 myid 文件内容就是“1”。注意,请确保每个服务器的 myid 文件中的数字不同,并且和自己所在机器的 zoo.conf 中 server.id=host:port:port 的 id 值一致。另外,id 的范围是 1~255。

下一步是创建 myid 文件。

在 dataDir 所配置的目录下,创建一个名为 myid 的文件,在该文件的第一行写上一个数字,和 zoo.conf 中当前机器的编号对应上。

按照相同的步骤,为其他机器都配置上 zoo.conf 和 myid 文件,然后启动服务器。

启动完后 ZooKeeper 后,查看服务状态如下:

ZooKeeper JMX enabled by default
Using config: /usr/local/etc/zookeeper/zoo2.cfg
Mode: leader

单机模式

一般情况下,在开发测试环境,我们没有那么多机器资源,而且平时的开发调试并不需要极好的稳定性。幸运的是,ZooKeeper 支持单机部署,只要启动一台 ZooKeeper 机器,就可以提供正常服务了。

其实,单机模式只是一种特殊的集群模式而已,只有一台机器的集群,认识到这点后,对下文的理解就会轻松不少了。单机模式的部署步骤和集群模式的部署步骤基本一致,只是在 zoo.conf 文件的配置上有些差异。由于现在我们是单机模式,整个 ZooKeeper 集群中只有一台机器,所以需要对 zoo.conf 做如下修改:

tickTime=2000
dataDir=/var/lib/zookeeper/
clientPort=2181
initLimit=10
syncLimit=5

查看 ZooKeeper 的状态,命令如下:

zkServer status

输出如下:

ZooKeeper JMX enabled by default
Using config: /usr/local/etc/zookeeper/zoo.cfg
Mode: standalone

集群模式和单机模式下输出的服务器信息基本一致,只有 Mode 属性不一样。在集群模式中,Mode 显示的是 leader,其实还有可能是 follower;而在单机模式中,Mode 显示的是 standalone。

伪集群模式

在介绍了集群和单机两种模式下,我们基本完成了分别针对生产环境和开发环境 ZooKeeper 服务的搭建,已经可以满足绝大多数场景了。现在我们再来看看另外一种情况,如果你手上有且只有一台比较好的机器一,那么这个时候,如果作为单机模式进行部署,资源明显有点浪费,而如果想要按照集群模式来部署的话,那么就需要借助硬件上的虚拟化技术,把一台物理机器转换成几台虚拟机,不过这样操作成本太高。所幸,和其他分布式系统(如 Hadoop)一样,ZooKeeper 也允许你在一台机器上完成一个伪集群的搭建。

所谓的伪集群,用一句话说就是,集群所有的机器都在一台机器上,但还是以集群的特性来对外提供服务。这种模式和集群模式非常类似,只是把 zoo.conf 做了如下修改:

tickTime=2000

# 目录路径
dataDir=/var/lib/zookeeper/data1

# 对外提供的端口
clientPort=2181
initLimit=10
syncLimit=5

#cluster conf
server.1=ip1:2887:3887
server.2=ip1:2888:3888
server.3=ip1:2889:3889

在 zoo.conf 配置中,每一行的机器列表配置都是同一个 IP 地址,但是后面的端口配置都已经不一样了。这其实不难理解,在同一台机器上启动多个进程,就必须绑定不同的端口。如上的配置,需要三个 zoo.conf 配置,其中端口和数据目录需要不一样。

运行服务

启动服务

启动 ZooKeeper 服务有 2 种常见方式:

  • 使用 ZooKeeper 自带的启动脚本,zkServer.sh,如下:

    sh zkServer.sh start
  • 使用 Java 命令行,如下:

    java -cp lib/zookeeper-3.4.9.jar:lib/slf4j-api-1.6.1.jar:lib/slf4j-log4j12-1.6.1.jar org.apache.zookeeper.server.quorum.QuorumPeerMain conf/zoo.conf

停止服务

停止 ZooKeeper 服务最常用的方法就是使用上面介绍的 zkServer 脚本的 stop 命令来完成,如下:

sh zkServer.sh stop

执行结果如下:

ZooKeeper JMX enabled by default
Using config: /usr/local/etc/zookeeper/zoo.cfg
Stopping zookeeper ... STOPPED