那曲檬骨新材料有限公司

0
  • 聊天消息
  • 系統消息
  • 評論與回復
登錄后你可以
  • 下載海量資料
  • 學習在線課程
  • 觀看技術視頻
  • 寫文章/發帖/加入社區
會員中心
創作中心

完善資料讓更多小伙伴認識你,還能領取20積分哦,立即完善>

3天內不再提示

ZAB協議巧妙的設計

科技綠洲 ? 來源:Java技術指北 ? 作者:Java技術指北 ? 2023-10-13 14:10 ? 次閱讀

一、Zookeeper 簡介

那聊 **ZAB **協議,先得看下 Zookeeper 是個什么玩意。

Zookeeper 是一個分布式數據一致性的解決方案,分布式應用可以基于它實現諸如數據發布/訂閱,負載均衡,命名服務,分布式協調/通知,集群管理,Master 選舉,分布式鎖和分布式隊列等功能。 Zookeeper 致力于提供一個高性能、高可用、且具有嚴格的順序訪問控制能力的分布式協調系統

好像確實挺牛逼的,能干這么多事呢,看來搞它是必須的呀!

考慮到 Zookeeper 主要操作數據的狀態,為了保證狀態的一致性,Zookeeper提出了兩個安全屬性:

  1. 全序(Total order):如果 消息 a 在 消息 b 之前發送,則所有 Server 應該看到相同的結果;
  2. 因果順序(Causal order):如果 消息 a 在 消息 b 之前發生(a 導致了b),并被一起發送,則 a 始終在 b 之前被執行;

為了保證上述兩個安全屬性,Zookeeper 使用了 TCP 協議 和 Leader

  1. 通過使用 TCP 協議保證了消息的全序特性(先發先到);
  2. 通過 Leader 解決了因果順序問題:先到 Leader 的先執行,但是這樣的話 Leader 有可能出現出現網絡中斷、崩潰退出與重啟等異常情況,這就有必要引入 Leader 選舉算法

而 ZAB(Zookeeper Atomic Broadcast 即 Zookeeper 原子消息廣播協議)正是作為其數據一致性的核心算法,下面介紹一下 ZAB 協議。

二、什么是 ZAB 協議

ZAB ,Zookeeper Atomic Broadcast,zk 原子消息廣播協議,是專為 ZooKeeper 設計的一 種支持崩潰恢復的原子廣播協議。在 Zookeeper 中,基于該協議,ZooKeeper 實現了一種主從模式的系統架構來保持集群中各個副本之間的數據一致性。

Zookeeper 使用一個單一主進程來接收并處理客戶端的所有事務請求,即寫請求。當服 務器數據的狀態發生變更后,集群采用 ZAB 原子廣播協議,以事務提案 Proposal 的形式廣 播到所有的副本進程上。ZAB 協議能夠保證一個全局的變更序列,即可以為每一個事務分配 一個全局的遞增編號 xid。

當 Zookeeper 客戶端連接到 Zookeeper 集群的一個節點后,若客戶端提交的是讀請求, 那么當前節點就直接根據自己保存的數據對其進行響應;如果是寫請求且當前節點不是 Leader,那么節點就會將該寫請求轉發給 Leader,Leader 會以提案的方式廣播該寫操作,只 要有超過半數節點同意該寫操作,則該寫操作請求就會被提交。然后 Leader 會再次廣播給 所有訂閱者,即 Learner,通知它們同步數據。

圖片

三、ZAB 協議原理

ZAB 協議要求每個 Leader 都要經歷三個階段: 發現,同步,廣播

  1. 發現 :要求 Zookeeper 集群必須選舉出一個 Leader 進程,同時 Leader 會維護一個 Follower 可用客戶端列表。將來客戶端可以和這些 Follower 節點進行通信
  2. 同步 :Leader 要負責將本身的數據與 Follower 完成同步,做到多副本存儲。這樣也是體現了CAP中的高可用和分區容錯。Follower 將隊列中未處理完的請求消費完成后,寫入本地事務日志中
  3. 廣播 :Leader 可以接受客戶端新的事務 Proposal 請求,將新的 Proposal 請求廣播給所有的 Follower。

四、ZAB 協議核心

ZAB 協議的核心:定義了事務請求的處理方式

  1. 所有的事務請求必須由一個全局唯一的服務器來協調處理,這樣的服務器被叫做 Leader 服務器 。其他剩余的服務器則是 Follower 服務器
  2. Leader 服務器 負責將一個客戶端事務請求,轉換成一個 事務 Proposal ,并將該 Proposal 分發給集群中所有的 Follower 服務器,也就是向所有 Follower 節點發送數據廣播請求(或數據復制)
  3. 分發之后Leader服務器需要等待所有 Follower 服務器的反饋(Ack請求),在ZAB 協議中,只要超過半數的 Follower 服務器進行了正確的反饋后(也就是收到半數以上的Follower的Ack請求),那么 Leader 就會再次向所有的 Follower 服務器發送 Commit 消息,要求其將上一個 事務 Proposal 進行提交。

圖片

五、ZAB 協議內容

ZAB 協議包括兩種基本的模式:崩潰恢復消息廣播

1.協議過程

當整個集群啟動過程中,或者當 Leader 服務器出現網絡中弄斷、崩潰退出或重啟等異常時,ZAB 協議就會 進入崩潰恢復模式 ,選舉產生新的 Leader。

當選舉產生了新的 Leader,同時集群中有過半的機器與該 Leader 服務器完成了狀態同步(即數據同步)之后,ZAB 協議就會退出崩潰恢復模式, 進入消息廣播模式

這時,如果有一臺遵守 ZAB 協議的服務器加入集群,那么因為此時集群中已經存在一個 Leader 服務器在廣播消息,那么該新加入的服務器自動進入恢復模式:找到 Leader 服務器,并且完成數據同步。同步完成后,作為新的 Follower 一起參與到消息廣播流程中。

2.協議狀態切換

當 Leader 出現崩潰退出或者機器重啟,亦或是集群中不存在超過半數的服務器與 Leader 保存正常通信,ZAB 就會再一次進入崩潰恢復,發起新一輪Leader 選舉并實現數據同步。同步完成后又會進入消息廣播模式,接收事務請求。

3.保證消息有序

在整個消息廣播中,Leader 會將每一個事務請求轉換成對應的 Proposal 來進行廣播,并且在廣播 事務 Proposal 之前,Leader 服務器會首先為這個事務 Proposal 分配一個全局單遞增的唯一ID,稱之為事務ID(即 zxid),由于 Zab 協議需要保證每一個消息的嚴格的順序關系,因此必須將每一個 Proposal 按照其 zxid 的先后順序進行排序和處理。

六、崩潰恢復

一旦 Leader 服務器出現崩潰或者由于網絡原因導致 Leader 服務器失去了與過半 Follower 的聯系,那么就會進入崩潰恢復模式。

前面我們說過,崩潰恢復具有兩個階段: Leader 選舉 與 初始化同步 。當完成 Leader 選 舉后,此時的 Leader 還是一個準 Leader,其要經過初始化同步后才能變為真正的 Leader。

初始化同步

圖片

具體過程如下:

  1. 為了保證 Leader 向 Learner 發送提案的有序,Leader 會為每一個 Learner 服務器準備一 個隊列;
  2. Leader 將那些沒有被各個 Learner 同步的事務封裝為 Proposal;
  3. Leader 將這些 Proposal 逐條發給各個 Learner,并在每一個 Proposal 后都緊跟一個 COMMIT 消息,表示該事務已經被提交,Learner 可以直接接收并執行 ;
  4. Learner 接收來自于 Leader 的 Proposal,并將其更新到本地;
  5. 當 Learner 更新成功后,會向準 Leader 發送 ACK 信息
  6. Leader 服務器在收到來自 Learner 的 ACK 后就會將該 Learner 加入到真正可用的 Follower 列表或 Observer 列表。沒有反饋 ACK,或反饋了但 Leader 沒有收到的 Learner,Leader 不會將其加入到相應列表。

七、恢復模式的兩個原則

當集群正在啟動過程中,或 Leader 與超過半數的主機斷連后,集群就進入了恢復模式。對于要恢復的數據狀態需要遵循兩個原則。

1. 已被處理過的消息不能丟

當 Leader 收到超過半數 Follower 的 ACKs 后,就向各個 Follower 廣播 COMMIT 消息, 批準各個 Server 執行該寫操作事務。當各個 Server 在接收到 Leader 的 COMMIT 消息后就會在本地執行該寫操作,然后會向客戶端響應寫操作成功。

但是如果在非全部 Follower 收到 COMMIT 消息之前 Leader 就掛了,這將導致一種后 果: 部分 Server 已經執行了該事務,而部分 Server 尚未收到 COMMIT 消息 ,所以其并沒有執行該事務。當新的 Leader 被選舉出,集群經過恢復模式后需要保證所有 Server 上都執行 了那些已經被部分 Server 執行過的事務。

2. 被丟棄的消息不能再現

當新事務在 Leader 上已經通過,其已經將該事務更新到了本地,但所有 Follower 還都沒有收到 COMMIT 之前,Leader 宕機了(比前面敘述的宕機更早),此時,所有 Follower 根本 就不知道該 Proposal 的存在。當新的 Leader 選舉出來,整個集群進入正常服務狀態后,之 前掛了的 Leader 主機重新啟動并注冊成為了 Follower。若那個別人根本不知道的 Proposal 還保留在那個主機,那么其數據就會比其它主機多出了內容,導致整個系統狀態的不一致。所以,該 Proposa 應該被丟棄。類似這樣應該被丟棄的事務,是不能再次出現在集群中的, 應該被清除。

八、消息廣播

當集群中的 Learner 完成了初始化狀態同步,那么整個 zk 集群就進入到了正常工作模式 了。

圖片

如果集群中的 Learner 節點收到客戶端的事務請求,那么這些 Learner 會將請求轉發給 Leader 服務器。然后再執行如下的具體過程:

  1. Leader 接收到事務請求后,為事務賦予一個全局唯一的 64 位自增 id,即 zxid,通過 zxid 的大小比較即可實現事務的有序性管理,然后將事務封裝為一個 Proposal。
  2. Leader 根據 Follower 列表獲取到所有 Follower,然后再將 Proposal 通過這些 Follower 的 隊列將提案發送給各個 Follower。
  3. 當 Follower 接收到提案后,會先將提案的 zxid 與本地記錄的事務日志中的最大的 zxid 進行比較。若當前提案的 zxid 大于最大 zxid,則將當前提案記錄到本地事務日志中,并 向 Leader 返回一個 ACK。
  4. 當 Leader 接收到過半的 ACKs 后,Leader 就會向所有 Follower 的隊列發送 COMMIT 消息,向所有 Observer 的隊列發送 Proposal。
  5. 當 Follower 收到 COMMIT 消息后,就會將日志中的事務正式更新到本地。當 Observer 收到 Proposal 后,會直接將事務更新到本地。
  6. 無論是 Follower 還是 Observer,在同步完成后都需要向 Leader 發送成功 ACK。

九、實現原理

1.三類角色

為了避免 Zookeeper 的單點問題,zk 也是以集群的形式出現的。zk 集群中的角色主要有 以下三類:

  • Leader:接收和處理客戶端的讀請求;zk 集群中事務請求的唯一處理者,并負責發起決議和投票,然后將通過的事務請求在本地進行處理后,將處理結果同步給集群中的其它主機。
  • Follower:接收和處理客戶端的讀請求; 將事務請求轉給 Leader;同步 Leader 中的數據;當 Leader 掛了,參與 Leader 的選舉(具有選舉權與被選舉權);
  • Observer:就是沒有選舉權與被選舉權,且沒有投票權的 Follower(臨時工)。若 zk 集 群中的讀壓力很大,則需要增加 Observer,最好不要增加 Follower。因為增加 Follower 將會增大投票與統計選票的壓力,降低寫操作效率,及 Leader 選舉的效率。

這三類角色在不同的情況下又有一些不同的名稱,在zookeeper源碼中的定義,可以了解下,看源碼可能會少點疑惑的。

  • Learner = Follower + Observer
  • QuorumServer = Follower + Leader

2.三個數據

在 ZAB 中有三個很重要的數據:

  • zxid:是一個 64 位長度的 Long 類型。其中高 32 位表示 epoch,低 32 表示 xid。
  • epoch:每個 Leader 都會具有一個不同的 epoch,用于區分不同的時期(可以理解為朝代的年號)
  • xid:事務 id,是一個流水號,(每次朝代更替,即 leader 更換),從0開始遞增。

每當選舉產生一個新的 Leader ,就會從這個 Leader 服務器上取出本地事務日志中最大編號 Proposal 的 zxid,并從 zxid 中解析得到對應的 epoch 編號,然后再對其加1,之后該編號就作為新的 epoch 值,并將低32位數字歸零,由0開始重新生成 zxid。

3.三種狀態

zk 集群中的每一臺主機,在不同的階段會處于不同的狀態。每一臺主機具有四種狀態。

  • LOOKING:選舉狀態
  • FOLLOWING:Follower 的正常工作狀態,從 Leader 同步數據的狀態
  • LEADING:Leader 的正常工作狀態,Leader 廣播數據更新的狀態

代碼實現中,多了一種狀態:Observing 狀態是 Zookeeper 引入 Observer 之后加入的,Observer 不參與選舉,是只讀節點,實際上跟 ZAB 協議沒有關系。這里為了閱讀源碼加上此概念。

  • OBSERVING:Observer 的正常工作狀態,從 Leader 同步數據的狀態

4.Zab 的四個階段

  • myid : 這是 zk 集群中服務器的唯一標識,稱為 myid。例如,有三個 zk 服務器,那么編號分別 是 1,2,3。
  • 邏輯時鐘 : 邏輯時鐘,Logicalclock,是一個整型數,該概念在選舉時稱為 logicalclock,而在選舉結 束后稱為 epoch。即 epoch 與 logicalclock 是同一個值,在不同情況下的不同名稱。
1).選舉階段(Leader Election)

節點在一開始都處于選舉節點,只要有一個節點得到超過半數節點的票數,它就可以當選準 Leader,只有到達第三個階段(也就是同步階段),這個準 Leader 才會成為真正的 Leader。

Zookeeper 規定所有有效的投票都必須在同一個 輪次 中,每個服務器在開始新一輪投票時,都會對自己維護的 logicalClock 進行自增操作

每個服務器在廣播自己的選票前,會將自己的投票箱(recvset)清空。該投票箱記錄了所收到的選票。

例如:Server_2 投票給 Server_3,Server_3 投票給 Server_1,則Server_1的投票箱為 (2,3)、(3,1)、(1,1)。(每個服務器都會默認給自己投票)

前一個數字表示投票者,后一個數字表示被選舉者。票箱中只會記錄每一個投票者的最后一次投票記錄,如果投票者更新自己的選票,則其他服務器收到該新選票后會在自己的票箱中更新該服務器的選票。

圖片

這一階段的目的就是為了選出一個準 Leader ,然后進入下一個階段。

2). 發現階段(Descovery)

在這個階段,Followers 和上一輪選舉出的準 Leader 進行通信,同步 Followers 最近接收的事務 Proposal 。

這個階段的主要目的是發現當前大多數節點接收的最新 Proposal,并且準 Leader 生成新的 epoch ,讓 Followers 接收,更新它們的 acceptedEpoch

3). 同步階段(Synchronization)

同步階段主要是利用 Leader 前一階段獲得的最新 Proposal 歷史,同步集群中所有的副本

只有當 quorum(超過半數的節點) 都同步完成,準 Leader 才會成為真正的 Leader。Follower 只會接收 zxid 比自己 lastZxid 大的 Proposal。

4). 廣播階段(Broadcast)

到了這個階段,Zookeeper 集群才能正式對外提供事務服務,并且 Leader 可以進行消息廣播。同時,如果有新的節點加入,還需要對新節點進行同步。需要注意的是,ZAB 提交事務并不像 2PC 一樣需要全部 Follower 都 Ack,只需要得到 quorum(超過半數的節點)的Ack 就可以。

十、ZAB 與 Paxos

上面已經針對 ZAB 協議涉及流程作了詳細的描述,那么它和 Paxos 是什么關系呢?

ZAB 的作者認為ZAB 與 Paxos 并不相同,之所以沒有采用 Paxos 是因為Paxos 保證不了全序順序:

Because multiple leaders can propose a value for a given instance two problems arise. First, proposals can conflict. Paxos uses ballots to detect and resolve conflicting proposals. Second, it is not enough to know that a given instance number has been committed, processes must also be able to fi gure out which value has been committed.

Paxos 算法的確是不關心請求之間的邏輯順序,而只考慮數據之間的全序,但很少有人直接使用 Paxos 算法,都會經過一定的簡化、優化。

Google的粗粒度鎖服務Chubby的設計開發者Burrows曾經說過:“ 所有一致性協議本質上要么是 Paxos 要么是其變體 ”。這句話還是有一定道理的,ZAB本質上就是 Paxos 的一種簡化形式。

總結:

本文主要講解了ZAB 上述一系列巧妙的設計,比如:為了加快收斂速度避免活鎖引發的競爭引入了 Leader 角色,在正常情況下最多只有一個參與者扮演 Leader角色,其他參與者扮演 Acceptor;在這種優化算法中,只有 Leader 可以提出議案,從而避免了競爭使得算法能夠快速地收斂而趨于一致;而為了保證 Leader 的健壯性,又引入了 Leader 選舉,再考慮到同步的階段,提出了消息廣播和崩潰初始化同步以及恢復模式的兩個原則。

聲明:本文內容及配圖由入駐作者撰寫或者入駐合作網站授權轉載。文章觀點僅代表作者本人,不代表電子發燒友網立場。文章及其配圖僅供工程師學習之用,如有內容侵權或者其他違規問題,請聯系本站處理。 舉報投訴
  • 數據
    +關注

    關注

    8

    文章

    7139

    瀏覽量

    89576
  • 服務器
    +關注

    關注

    12

    文章

    9303

    瀏覽量

    86061
  • 網絡
    +關注

    關注

    14

    文章

    7599

    瀏覽量

    89250
收藏 人收藏

    評論

    相關推薦

    巧妙的點焊機電路

    .該點焊機有三擋功率調節,還有一個細調旋鈕,電路設計巧妙,制作并不復雜
    發表于 04-02 12:22 ?2.3w次閱讀
    <b class='flag-5'>巧妙</b>的點焊機電路

    光電轉換電路中對微弱信號的巧妙處理

    光電轉換電路中對微弱信號的巧妙處理
    發表于 03-17 23:19

    教你幾個電流檢測電路的巧妙技巧

    用招就要用妙招,今天樓主來教大家幾個電流檢測電路的巧妙技巧。要知道在電源等設備中通常需要做電流檢測或反饋,電流檢測通常用串聯采樣電阻在通過放大器放大電阻上的電壓的方法,如果要提高檢測精度這地方往往
    發表于 01-20 16:03

    永動機?設計很巧妙啊!

    `設計很巧妙啊!`
    發表于 10-18 19:57

    如何巧妙地用繼電器實現直流電機正反轉?

    如何巧妙地用繼電器實現直流電機正反轉?
    發表于 10-14 08:21

    如何巧妙利用USB端口控制電視機與機頂盒的供電?

    如何巧妙利用USB端口控制電視機與機頂盒的供電?
    發表于 02-22 08:31

    TMS320VC5416并行自舉的巧妙實現

    摘要:提出了一種巧妙實現DSP并行自舉的方法,即采用“兩次下載法”,利用DSP自身對FLASH編程,以實現DSP的并行自舉。這種在系統編程的DSP自舉實現方式無需文件
    發表于 03-11 17:39 ?1528次閱讀
    TMS320VC5416并行自舉的<b class='flag-5'>巧妙</b>實現

    [圖文]設計巧妙的數顯搶答器

    2002年,第18期,類別:電子產品與器件    本搶答器通過十分巧妙
    發表于 04-15 23:05 ?755次閱讀

    巧妙的冷接點補償方法電路圖

    巧妙的冷接點補償方法電路圖
    發表于 07-16 17:44 ?592次閱讀
    <b class='flag-5'>巧妙</b>的冷接點補償方法電路圖

    妙用搜索快照巧妙突破限制

    妙用搜索快照巧妙突破限制      在我們借助百度搜索引擎查找資料時,打開的鏈接經常碰到要注冊才能查看,甚至
    發表于 02-23 14:44 ?452次閱讀

    溫度巡檢儀中恒流源電路的巧妙設計

    本文主要介紹了在 溫度巡檢儀 系統中 恒流源電路 的巧妙設計,系統采用恒流源電路作為信號的獲取電路,恒流源電路是采用價格低廉的器件通過比較巧妙的設計構成的,恒流效果十分理想
    發表于 08-09 10:57 ?79次下載
    溫度巡檢儀中恒流源電路的<b class='flag-5'>巧妙</b>設計

    電阻的巧妙用法

    電阻的巧妙用法
    發表于 12-16 12:59 ?0次下載

    51內核軟件延時和串口的巧妙方法介紹

    51內核軟件延時和串口的巧妙方法介紹,具體的跟隨小編一起來了解一下。
    的頭像 發表于 07-28 11:28 ?4179次閱讀
    51內核軟件延時和串口的<b class='flag-5'>巧妙</b>方法介紹

    STM32Cbue LL庫中巧妙運用“靜態內聯”

    STM32的標準外設庫、HAL、LL軟件庫,都有很多巧妙之處值得大家借鑒。 今天講講STM32Cbue LL庫中巧妙運用“靜態內聯”使代碼更高效。
    發表于 08-14 14:30 ?1199次閱讀

    STM32Cube LL庫的巧妙之處

    STM32Cube LL庫的巧妙之處
    的頭像 發表于 09-27 16:26 ?1473次閱讀
    STM32Cube LL庫的<b class='flag-5'>巧妙</b>之處
    娱乐城注册送38彩金| 星河百家乐官网现金网| 大发888娱乐亚洲| 金杯百家乐的玩法技巧和规则| 百家乐真钱游戏下载| 百家乐官网博彩吧| 百家乐官网大路图| 百家乐官网半圆桌| 兴和县| 时时博娱乐城| 516棋牌游戏加速器| 大发888娱乐城欢迎您| 百家乐庄闲对冲| 网络百家乐路单图| 20人百家乐官网桌| 火箭百家乐官网的玩法技巧和规则| 金盾百家乐官网网址| 百家乐官网游戏真钱游戏| 宣武区| 晋江市| 大安市| 长汀县| 汉川市| 张家界市| 百家乐投注| ewin娱乐城官方下载| 乐九| 金樽国际娱乐| 优博最新网址| 御匾会娱乐城| 澳门赌场| 视频百家乐| 大冶市| 阳泉市| 百家乐官网对子赔率| 军事| 南皮县| 战神线上娱乐| 鼎丰娱乐城| 克东县| 百家乐官网游戏软件开发|