ZooKeeper系列(1):安裝搭建ZooKeeper環境


ZooKeeper系列文章:https://www.cnblogs.com/f-ck-need-u/p/7576137.html#zk

 


ZooKeeper有三種安裝模式:單機安裝(standalone)、偽集群模式、集群模式:

  • standalone模式:只在一台機器上安裝ZooKeeper,並只啟動一個ZooKeeper實例。
  • 偽集群:在一台機器上開啟多個ZooKeeper實例來模擬集群。通過加載不同配置文件,分配不同數據目錄來實現這種模式。因為在同一機器上運行,所以機器宕機,整個ZooKeeper就掛了。基本上不會布置這樣的ZooKeeper集群。
  • 集群模式:在至少3台機器上安裝ZooKeeper構成集群,只要故障節點數量在一定范圍內就能保證ZooKeeper服務的可用性。

真正布置的基本上都是集群模式,standalone偶爾用來做些測試,它有單點故障,偽集群模式也有單點故障。

集群模式並非一定至少3台機器,但用2台機器比1台機器更危險,因為隨便故障一台都無法滿足"大多數"的要求,都會阻塞整個ZooKeeper服務。而2台機器的故障幾率是1台機器的2倍。所以,也建議采用奇數台機器來部署ZooKeeper。

ZooKeeper下載:https://mirrors.tuna.tsinghua.edu.cn/apache/zookeeper/stable/

我下載的是3.4.12版本。

1.安裝jdk

ZooKeeper運行在java環境下,所以需要先安裝jdk,且要求版本高於1.6。

jdk下載:http://www.oracle.com/technetwork/java/javase/downloads/index.html

以rpm包的為例。

yum localinstall -y jdk-8u131-linux-x64.rpm

rpm包的安裝路徑為/usr/java。

[root@s1 ~]# ls -l /usr/java/
total 4
lrwxrwxrwx 1 root root   16 Jun 26 22:53 default -> /usr/java/latest
drwxr-xr-x 9 root root 4096 Jun 26 22:53 jdk1.8.0_131
lrwxrwxrwx 1 root root   22 Jun 26 22:53 latest -> /usr/java/jdk1.8.0_131

通過這種軟鏈接方式,以后有新版jdk要安裝,直接改latest的鏈接對象即可。

然后再設置JAVA_HOME環境變量並導出java程序所在目錄的PATH環境變量。

echo 'JAVA_HOME=/usr/java/latest' > /etc/profile.d/jdk.sh
echo 'PATH=$JAVA_HOME/bin:$PATH' >> /etc/profile.d/jdk.sh
chmod +x /etc/profile.d/jdk.sh
source /etc/profile.d/jdk.sh

2.StandAlone模式

standalone模式是在單機上安裝ZooKeeper。

先解壓zookeeper-3.4.12.tar.gz。

tar xf zookeeper-3.4.12.tar.gz

再把它移到/usr/local/下方便管理。

mv zookeeper-3.4.12 /usr/local/zookeeper

在ZooKeeper的bin目錄下提供了幾個Windows和Linux下的腳本:

[root@s2 zookeeper]# cd /usr/local/zookeeper
[root@s2 zookeeper]# ls bin
README.txt  zkCleanup.sh  zkCli.cmd  zkCli.sh  zkEnv.cmd  zkEnv.sh  zkServer.cmd  zkServer.sh
  • zkServer:用於啟動、停止ZooKeeper,且能查看ZooKeeper狀態。
zkServer.sh {start|start-foreground|stop|restart|status|upgrade|print-cmd}
  • zkEnv:設置ZooKeeper啟動、關閉時的環境變量。在其余的每個腳本中都引用了這個腳本。
  • zkCleanup:清除ZooKeeper的事務日志和快照。
  • zkCli:ZooKeeper的一個命令行客戶端。

設置ZooKeeper的環境變量,這不是必須的,只是為了方便操作上面的幾個腳本。

echo 'ZOOKEEPER_HOME=/usr/local/zookeeper' >/etc/profile.d/zk.sh
echo 'PATH=$ZOOKEEPER_HOME/bin:$PATH' >> /etc/profile.d/zk.sh
chmod +x /etc/profile.d/zk.sh
source /etc/profile.d/zk.sh

把windows下的腳本刪除:

rm -rf /usr/local/zookeeper/bin/{*.cmd,README.txt}

為了啟動ZooKeeper,先提供一個配置文件。默認配置文件的路徑為$ZOOKEEPER_HOME下的conf目錄。在這個目錄下,有幾個文件:

[root@s2 zookeeper]# ls conf
configuration.xsl  log4j.properties  zoo_sample.cfg
  • configuration.xsl:無視它。
  • log4f.properties:是ZooKeeper的日志配置文件。
  • zoo_sample.cfg:是ZooKeeper的示例配置文件。

zkServer.sh默認的配置文件名為zoo.cfg。所以,在conf目錄下創建一個zoo.cfg。寫入幾個保證ZooKeeper能正常運行的配置項:

tickTime=2000
dataDir=/usr/local/zookeeper/data1
clientPort=2181

其中:

  • tickTime:ZooKeeper中很多配置項(如心跳時間、連接超時時間等)都要用到的時間單位,這里配置為2000毫秒,即2秒。
  • dataDir:ZooKeeper實例的數據目錄。
  • clientPort:ZooKeeper向外提供服務的端口。

然后用zkServer.sh來啟動ZooKeeper。

[root@s2 zk]# zkServer.sh start
ZooKeeper JMX enabled by default
Using config: /usr/local/zookeeper/bin/../conf/zoo.cfg
Starting zookeeper ... STARTED

也可以手動指定啟動時讀取的配置文件:

[root@s2 zk]# zkServer.sh start /usr/local/zookeeper/conf/zoo.cfg

查看ZooKeeper的運行狀態:

[root@s2 zk]# zkServer.sh status
ZooKeeper JMX enabled by default
Using config: /usr/local/zookeeper/bin/../conf/zoo.cfg
Mode: standalone

可以看到運行模式是"standalone"。

ZooKeeper啟動后,就可以向外提供ZooKeeper服務了。這里用ZooKeeper提供的命令行客戶端去連接一下ZooKeeper做個簡單的測試。

連接ZooKeeper實例:

zkCli.sh -server localhost:2181

連接過程中會輸出一大堆信息。當連接成功后,將進入ZooKeeper的交互式模式:

WatchedEvent state:SyncConnected type:None path:null

[zk: localhost:2181(CONNECTED) 0]   # 在這里輸入ZooKeeper允許的命令

例如,創建一個znode:

[zk: localhost:2181(CONNECTED) 0] create /zk_test mydata1
Created /zk_test
[zk: localhost:2181(CONNECTED) 1] ls /
[zookeeper, zk_test]

[zk: localhost:2181(CONNECTED) 2] quit

3.配置偽集群模式

ZooKeeper的偽集群模式是在一個服務器上運行多個ZooKeeper實例來模擬ZooKeeper集群。偽集群模式下,每個實例的配置文件不同、數據目錄不同、端口不同。一般來說,ZooKeeper集群至少需要3個服務器節點。

這里,我配置3個實例的ZooKeeper偽集群,它們的數據目錄分別為$ZOOKEEPER_HOME下的data1、data2和data3。因為稍后要向這些目錄中寫myid文件,所以先創建這3個目錄:

mkdir /usr/local/zookeeper/data{1,2,3}

先提供3個實例的配置文件,分別為$ZOOKEEPER_HOME/conf/{zoo1.cfg,zoo2.cfg,zoo3.cfg}

以下是zoo1.cfg內容,各配置項稍后解釋。

tickTime=2000
dataDir=/usr/local/zookeeper/data1
clientPort=2181
initLimit=5
syncLimit=2
server.1=localhost:2887:3887
server.2=localhost:2888:3888
server.3=localhost:2889:3889

以下是zoo2.cfg內容,各配置項稍后解釋。

tickTime=2000
dataDir=/usr/local/zookeeper/data2
clientPort=2182
initLimit=5
syncLimit=2
server.1=localhost:2887:3887
server.2=localhost:2888:3888
server.3=localhost:2889:3889

以下是zoo3.cfg內容,各配置項稍后解釋。

tickTime=2000
dataDir=/usr/local/zookeeper/data3
clientPort=2183
initLimit=5
syncLimit=2
server.1=localhost:2887:3887
server.2=localhost:2888:3888
server.3=localhost:2889:3889

上面的配置項中:

  • initLimit:當非leader節點(即follower和observer)啟動時,需要先從leader那里復制數據,以保證所有ZooKeeper節點數據都是同步的。這個選項設置非leader節點從啟動到完成同步的超時時長,它以tickTime為時間單位,所以上面的超時時長為5*2=10秒。

    一般來說,ZooKeeper保存的都是協調數據,數據量並不大,所以多數時候可以忽略這個參數,如果待同步數據真的很大,可以考慮增加這個超時時間。

  • syncLimit:follower和leader之間數據延遲的最大時間長度。例如,有個節點的更新操作緩慢,它的數據已經嚴重落后於leader,ZooKeeper就會將它從ZooKeeper集群中踢出去。ZooKeeper使用時間來度量follower和leader之間數據的延遲,這個選項的值依賴於tickTime,例如tickTime=2000,syncLimit=2表示follower比leader延遲了4秒。

  • server.X=[hostname]:port_A:port_B:該選項用來指定ZooKeeper集群中的服務器節點。其中:

    • X:整數。是ZooKeeper中服務器的一個簡單標識。這個數值需要和dataDir下的myid文件內容一致。在啟動ZooKeeper集群中的每個實例時,需要讀取數據目錄中的myid文件,並將該文件中的數值和配置文件中的server.X做匹配,匹配到哪個就表示是哪個ZooKeeper服務器節點。
    • hostname:ZooKeeper服務器節點的地址。
    • port_A:這是第一個端口,用於Follower和Leader之間的數據同步和其它通信。
    • port_B:這是第二個端口,用於Leader選舉過程中投票通信。

所以,分別在每個實例的dataDir下創建對應的myid文件。

echo 1 >/usr/local/zookeeper/data1/myid
echo 2 >/usr/local/zookeeper/data2/myid
echo 3 >/usr/local/zookeeper/data3/myid

然后啟動這3個ZooKeeper實例。

zkServer.sh start /usr/local/zookeeper/conf/zoo1.cfg
zkServer.sh start /usr/local/zookeeper/conf/zoo2.cfg
zkServer.sh start /usr/local/zookeeper/conf/zoo3.cfg

查看當前java進程列表:

[root@s1 zk]# jps -l
5473 org.apache.zookeeper.server.quorum.QuorumPeerMain
5395 org.apache.zookeeper.server.quorum.QuorumPeerMain
5427 org.apache.zookeeper.server.quorum.QuorumPeerMain
5524 sun.tools.jps.Jps

查看這3個實例之間的關系:zoo2.cfg被選為leader,其它是follower。

[root@s1 zk]# zkServer.sh status /usr/local/zookeeper/conf/zoo3.cfg
ZooKeeper JMX enabled by default
Using config: /usr/local/zookeeper/conf/zoo3.cfg
Mode: follower

[root@s1 zk]# zkServer.sh status /usr/local/zookeeper/conf/zoo1.cfg
ZooKeeper JMX enabled by default
Using config: /usr/local/zookeeper/conf/zoo1.cfg
Mode: follower

[root@s1 zk]# zkServer.sh status /usr/local/zookeeper/conf/zoo2.cfg
ZooKeeper JMX enabled by default
Using config: /usr/local/zookeeper/conf/zoo2.cfg
Mode: leader

可以用ZooKeeper提供的命令行客戶端工具來測試,寫入其中一個實例的數據,其它實例也能收到。

[root@s1 zk]# zkCli.sh -server localhost:2181 create /my_znode hello
......省略.........
WatchedEvent state:SyncConnected type:None path:null
Created /my_znode


[root@s1 zk]# zkCli.sh -server localhost:2182 ls /
......省略........
WatchedEvent state:SyncConnected type:None path:null
[my_znode, zookeeper]

4.配置ZooKeeper集群

以3節點的集群為例:192.168.100.21、192.168.100.22、192.168.100.23。因為前面配置單機ZooKeeper和偽集群ZooKeeper已經解釋過所有步驟和配置項的意義,所以這里就直接給步驟。

假設已經在3個節點上都安裝好了jdk(這是前提),並下載好了ZooKeeper。

先解壓zookeeper-3.4.12.tar.gz。

# 3個節點都執行
tar xf zookeeper-3.4.12.tar.gz
mv zookeeper-3.4.12 /usr/local/zookeeper

添加ZooKeeper環境變量,非必須過程,但建議。

# 在3節點上都執行
echo 'ZOOKEEPER_HOME=/usr/local/zookeeper' >/etc/profile.d/zk.sh
echo 'PATH=$ZOOKEEPER_HOME/bin:$PATH' >> /etc/profile.d/zk.sh
chmod +x /etc/profile.d/zk.sh
source /etc/profile.d/zk.sh

提供配置文件。以下是3個節點上的配置文件:

[root@s1 zk]# cat /usr/local/zookeeper/conf/zoo.cfg 
tickTime=2000
dataDir=/usr/local/zookeeper/data
clientPort=2181
initLimit=5
syncLimit=2
server.1=192.168.100.21:2888:3888
server.2=192.168.100.22:2888:3888
server.3=192.168.100.23:2888:3888

在三個節點上都創建好數據目錄,並寫入myid文件。

# 3個節點上都執行:
mkdir /usr/local/zookeeper/data

# 192.168.100.21上執行
echo 1 >/usr/local/zookeeper/data/myid

# 192.168.100.22上執行
echo 2 >/usr/local/zookeeper/data/myid

# 192.168.100.23上執行
echo 3 >/usr/local/zookeeper/data/myid

啟動這3個ZooKeeper實例。

# 3個節點都執行:
zkServer.sh start

然后在3個節點上都驗證一下是否正確啟動ZooKeeper。

# 節點1上執行:
[root@s1 zk]# zkServer.sh status
ZooKeeper JMX enabled by default
Using config: /usr/local/zookeeper/bin/../conf/zoo.cfg
Mode: follower

# 節點2上執行:
[root@s2 zk]# zkServer.sh status
ZooKeeper JMX enabled by default
Using config: /usr/local/zookeeper/bin/../conf/zoo.cfg
Mode: follower

# 節點3上執行:
[root@s3 zk]# zkServer.sh status
ZooKeeper JMX enabled by default
Using config: /usr/local/zookeeper/bin/../conf/zoo.cfg
Mode: leader

如果某個服務器實例出現了錯誤,請zkServer.sh stop關閉ZooKeeper實例,然后jps命令查看下是否還有ZooKeeper實例在運行,如果有,kill掉。然后再啟動ZooKeeper。另外,建議在第一次啟動ZooKeeper之前,先將dataDir/version-2目錄刪除(如果已存在,因為可能是以前的實例因為各種原因而留下來的)。

最后測試下,某節點上創建一個znode,其它節點是否也同步了該節點。

# 在192.168.100.21上創建一個znode:
[root@s2 zk]# zkCli.sh -server 192.168.100.21:2181 create /test_znode "hello world"
Connecting to 192.168.100.21:2181
.........省略..........
Created /test_znode

# 在192.168.100.22上獲取這個znode
[root@s2 zk]# zkCli.sh -server 192.168.100.22:2181 get /test_znode
Connecting to 192.168.100.22:2181
.........省略..........
hello world
cZxid = 0x100000002
ctime = Wed Jun 27 08:14:38 CST 2018
mZxid = 0x100000002
mtime = Wed Jun 27 08:14:38 CST 2018
pZxid = 0x100000002
cversion = 0
dataVersion = 0
aclVersion = 0
ephemeralOwner = 0x0
dataLength = 11
numChildren = 0

# 在192.168.100.23上獲取這個znode
[root@s2 zk]# zkCli.sh -server 192.168.100.23:2181 ls /
Connecting to 192.168.100.23:2181
.........省略..........
[zookeeper, test_znode]


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM