启动zookeeper_Zookeeper原理篇-Zookeeper启动流程分析
前言
上篇我們通過了解Paoxs算法開始,到Zab協議的兩大特性:崩潰恢復和消息廣播,學習了Zookeeper是如何通過Zab協議實現高可用,本篇開始我們來學習Zookeeper的啟動流程
單機模式啟動流程
我們知道,Zookeeper使用中分為單機和集群兩種,而這兩種最大的不同則是,集群啟動下需要進行Leader選舉以及Leader和Follower之間的數據同步操作,而單機啟動則不需要此操作,Zookeeper單機啟動大概分為三個部分,分別為預處理、初始化和注冊,接下來我們分別來看看三個流程的步驟
預處理
預處理操作中,將創建服務實例之前需要的數據讀取加載準備就緒,大體流程如下:
1.首先我們在使用zkServer.sh或者zkServer.cmd這兩個腳本啟動Zookeeper的時候,默認會啟動 org.apache.zookeeper.server.quorum.QuorumPeerMain類,因此無論是Zookeeper的單機還是集群環境下, QuormPeerMain類都是作為默認的入口啟動類啟動。
2.啟動后就會開始解析Zoo.cfg配置文件,從中讀取默認配置的tickTime、dataDir和clientPort等
3.當配置讀取并解析完畢以后,會創建 DatadirCleanupManager類實例,此類是Zookeeper從3.4版本開始加入的對歷史記錄文件進行清理以及定時清理日志和快照的管理器
4.從剛剛讀取解析的Zoo.cfg配置文件內容中找到clientPort參數內容,通過配置的地址判斷是否存在多個地址來確定當前啟動的模式是單機版還是集群模式,如果當前啟動模式為單機模式,將進入單機的啟動流程,并且讀取Zoo.cfg剩余的配置信息
5.通過解析Zoo.cfg中的配置信息相關的參數,開始創建ZookeeperServer類實例,完成了這一步后,預處理階段完成
初始化
初始化階段,則是開始將Zookeeper中的相關服務管理類進行創建,大體流程如下:
1.創建了ZookeeperServer實例后,Zookeeper會創建一個ServerStats實例,此類用來收集Zookeeper運行過程中的統計信息,例如發送客戶端的響應包次數,收到的請求包次數,最近啟動后最大的延遲和最小延遲等
2.緊接著會創建Zookeeper中的數據存儲管理器--FileTxnSnaplog類,此類作為最上層的,提供了一系列了操作數據文件的接口,其中包括操作事務日志和操作快照的接口,而創建當前類實例會根據zoo.cfg中的dataDir以及dataLogDir參數進行構建
3.同樣根據解析出來的zoo.cfg配置文件中的tickTime以及session的會話時間來設置對應參數,并且會根據zookeeper.serverCnxnFactory參數來確定啟動Zookeeper的網絡連接工廠是基于Netty的還是基于jdk自身的Nio工廠
4.確定工廠類型后,Zookeeper會開始初始化一個Thread,作為整個Zookeeper運行過程中的主線程,并且開始初始化ServerCnxnFactory實例
5.當ServerCnxnFactory實例構建完畢后,開始運行對應的run方法中的業務邏輯,此時由于連接工廠已經創建,端口其實已經對外開放了,但是Zookeeper此時還未完成啟動過程,還無法對外處理請求
6.開始恢復Zookeeper的數據,將從事務日志以及之前保存的快照進行數據恢復
7.數據恢復完成后,Zookeeper開始構建會話管理器--SessionTracker,此類主要負責管理Session,在創建的時候,將e xpirationlnterval, nextExpirationTime和 sessionsWithTimeout進行計算以及配置,并且會計算出每一個Session對應的SessionID,并且在運行過程中會負責Session的會話超時檢測等
8.創建完畢后,Zookeeper會初始化對應的請求過濾鏈,而在Zookeeper中請求的過濾鏈使用了責任鏈模式,其中處理的順序流程主要是PrepRequestProessor->SyncRequestProessor->FinalRequestProessor三個請求處理器,至此Zookeeper的初始化流程已經做完
注冊提供服務
當Zookeeper的初始化流程完成后,服務器已經開始到就緒狀態了,只需要將對應的信息注冊以后即可對外提供服務了,此階段的流程大概如下:
可以看到此階段中,Zookeeper只需要將JMX服務注冊,以及當前相關實例注冊完畢,即可完成單機啟動流程,此時的Zookeeper已經正常提供服務了
集群模式啟動流程
集群模式的啟動過程很多和單機模式是一樣的,但是由于集群模式下,會有Leader機器選舉以及數據同步的過程,因此Zookeeper的集群模式啟動過程要復雜的多,而整個集群的啟動過程,大體可以分為五個部分,分別是預處理、初始化、Leader選舉、Leader與Follower交互以及Leader與Follower啟動,其中預處理過程幾乎與單機模式一樣,唯一的區別在于解析zoo.cfg中的連接配置,判斷啟動模式為集群模式,開始進入集群模式的初始化操作流程而已,因此,我們從集群模式的初始化開始
初始化
初始化過程大體和單機模式差不多,如下:
1.創建并初始化ServerCnxnFactory
2.創建Zookeeper中的數據文件管理器FileTxnSnaplog
3.在集群模式下,會去創建QuorumPeer實例,Quorum是集群模式下特有的對象,屬于Zookeeper的托管者,此類的作用是在運行期間,會不停的檢測當前服務器實例的狀態,并且在需要選舉的時候發起選舉
4.創建Zookeeper中的內存數據庫ZKDatabase實例,用來記錄會話記錄以及DataTree和事物日志
5.QuorumPeer實例作為托管者,會在啟動過程中,將核心組件信息注冊上去,包括之前創建的ZKDatabase、FileTxnSnaplog以及服務器列表信息,選舉算法等
6.開始恢復數據
7.數據恢復完成后,開始啟動ServerCnxnFactory中的主線程,運行run方法,開始執行服務器選舉相關的操作
Leader選舉
選舉階段的流程大概如下:
1.Zookeeper解析zoo.cfg配置文件中的 electionAlg屬性,來確定進行選舉的算法是哪一種,在Zk中有三種選舉算法,分別是 LeaderElection 、 AuthFastLeaderElection 和FastLeaderElection,分別對應數值0-3,不過從3.4的版本開始,zk僅支持FastLeaderElection選舉算法,其他兩種被廢棄了。同樣的,在選舉的初始化階段,zk會根據自身服務器ID、lastLoggedZxid和當前服務器的epoch初始化一個選舉的票據
2.選舉初始化準備好以后,開始注冊JMX服務
3.前面創建好的QuorumPeer實例會不斷檢測當前的服務器狀態,在正常情況下,QuorumPeer的狀態應該是LOOKING,才會開始進行選舉操作
4.開始進行選舉操作,簡單來說,zk中一般是ZXID最大的機器成為Leader,如果ZXID一樣,SID越大的則成為Leader。(zk的詳細選舉流程,則在后續的文章中分析)
Leader與Follower交互
當選舉出Leader機器以后,其他的機器則會開始與Leader進行交互,進行數據同步等操作,此階段的流程大致如下:
1.不同角色(Leader和Follower)的zookeeper服務器在選舉完畢后,會開始進入各自角色的主流程
2.在Zookeeper集群運行期間,Leader服務器需要和其他的服務器保持連接確定集群的機器存活情況,zk創建LearnerCnxAcceptor實例用來負責處理所有的非Leader機器的連接請求
3.非Leader服務器在啟動完畢后,會從選舉的結果中找到集群的Leader,并且嘗試進行連接
4.Leader的LearnerCnxAcceptor實例在接受到非Leader機器的請求后,會創建LearnerCnxHandler實例,每個實例會對應一個Leader與非Leader機器的連接,負責對應服務器之間的消息通信處理以及數據同步操作
5.當非Leader機器與Leader服務器建立連接后,非Leader機器就會將自己的信息發送給Leader,此過程的數據稱之為LearnerInfo,其中包括了當前服務器的SID以及最大的ZXID
6.Leader收到LearnerInfo消息后,從中解析出SID和ZXID,然后根據ZXID解析出epochoflearner,和Leader自身的epochofleader進行比較,如果發現Leader的epochofleader比較小,則會更新Leader的epoch:
1. `epoch_of_leader = epoch_of_learner + 1`然后繼續等待其他機器的LearnerInfo消息,直到半數以上,即可確定整個集群中的epoch值了
7.在確定了epoch以后,Leader將該信息發送給所有的非Leader機器,此消息稱之為LEADERINFO
8.Follower機器在收到Leader發送的LEADERINFO消息后,解析出消息中的epoch和ZXID,然后響應給Leader一個ack
9.Leader收到ack以后,就可以開始與該Follower機器進行數據同步過程了
10.整個集群中如果超過半數的Follower機器完成了和Leader之間的數據同步過程,這個時候集群實例就已經可以提前啟動對外提供服務
Leader和Follower啟動
集群模式下的Zookeeper在完成了Leader與Follower服務器之間的交互流程后,也開始進入到了啟動注冊的階段,此階段和單機模式流程幾乎相同,首先是創建并且啟動會話管理器,然后初始化Zookeeper中的請求處理鏈,接著Zookeeper開始注冊JMX服務,當注冊完畢后,整個集群的啟動完成,此時Zookeeper的集群也可以對外開始提供服務了
總結
以上是生活随笔為你收集整理的启动zookeeper_Zookeeper原理篇-Zookeeper启动流程分析的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: python3的socket_pytho
- 下一篇: python processpoolex