Kafka-Zookeeper解析

在hyperledger fabric的orderer中挚躯,目前發(fā)布的版本是使用kafka來做排序片林,并沒有用到所謂的sbft譬涡。kafka作為一個消息中間件,來對orderer發(fā)過來的消息進行排序料皇,這樣所有的orderer可以當做consumer來去kafka上去取消息谓松。kafka具體和fabric怎么合作星压,我們按下不表。這篇文章主要介紹kafka的工作原理鬼譬,以及怎樣和zookeeper合作娜膘。



Zookeeper的原理

1. Zookeeper是什么

ZooKeeper是一種為分布式應(yīng)用所設(shè)計的高可用、高性能且一致的開源協(xié)調(diào)服務(wù)优质,它提供了一項基本服務(wù):分布式鎖服務(wù)竣贪。由于ZooKeeper的開源特性,后來我們的開發(fā)者在分布式鎖的基礎(chǔ)上巩螃,摸索了出了其他的使用方法:配置維護贾富、組服務(wù)、分布式消息隊列牺六、分布式通知/協(xié)調(diào)等。

2. 為什么要用Zookeeper

分布式節(jié)點的各個節(jié)點的協(xié)調(diào)是分布式服務(wù)必須要解決的一個問題汗捡。舉個例子來說明

為什么要使用分布式節(jié)點呢淑际?是為了解決所謂的單點故障。什么是單點故障呢扇住?如下圖所示春缕,一個主節(jié)點Master提供服務(wù)給其他機器,那么如果這個Master節(jié)點掛了呢艘蹋?是不是Slave從節(jié)點就無法享受到該服務(wù)了呢锄贼?


一般對這種單點故障的解決辦法是雙Master或者多集群。如下圖所示女阀,采用兩個Master宅荤,一個為主節(jié)點,一個為備份節(jié)點浸策。一旦發(fā)現(xiàn)主節(jié)點有問題(掛了或者出錯)冯键,則立即切換到備份節(jié)點。



如下圖所示庸汗,所有的slave在收到消息后惫确,直接切換到備用節(jié)點。

然而在有時候主節(jié)點沒有宕機蚯舱,然而Slave節(jié)點或者其他Master節(jié)點認為他宕機了改化,這樣極其容易造成彼此之間的視圖(對整個集群的理解)不一致。如下圖所示:


當集群中的節(jié)點出現(xiàn)對集群的理解不一致時枉昏,會對強一致性的程序產(chǎn)生很壞的影響陈肛,有可能會造成消息的亂序。所以一致性問題的解決有很多辦法凶掰,比如PBFT燥爷,RAFT或者鎖等等蜈亩。每種辦法都有各自的優(yōu)劣。

那么Zookeeper的引入前翎,怎么能解決這個全局視圖保證一致呢稚配?

如下圖所示,主節(jié)點A和主節(jié)點B在啟動的時候港华,都首先向Zookeeper節(jié)點注冊道川,Zookeeper會將這兩個節(jié)點寫入到自己的文件系統(tǒng)內(nèi),并分配給每個節(jié)點一個id號立宜。與此同時冒萄,Zookeeper節(jié)點會保持與兩個Master節(jié)點的心跳,每隔幾個tick(自己定義在配置文件里)與節(jié)點溝通一次橙数,以此驗證節(jié)點的狀態(tài)尊流。這樣哪個節(jié)點宕機,哪個節(jié)點新加入等等都可以實時的反應(yīng)在zookeeper上灯帮。Slave節(jié)點想知道連哪個主節(jié)點崖技,根據(jù)自己的算法去選擇。比如kafka就會根據(jù)topic隨機選擇leader钟哥。所有人都可以在zookeeper上設(shè)置監(jiān)聽迎献,一旦某個主節(jié)點有變動,大家都會收到zookeeper的推送消息腻贰。

寫到這里估計有人得問吁恍,你這不也會有單點故障的風險嗎?比如這個zookeeper掛了怎么辦播演?這個問題是個好問題冀瓦。zookeeper可以設(shè)置集群,也就是幾個zookeeper可以同時對外服務(wù)宾巍。那么zookeeper集群如何保證一致性的咕幻?怎樣保證所有的zookeeper對外部世界的理解一致的?總不能這個zookeeper知道MasterA是正常的顶霞,那個zookeeper以為MasterA是不正常吧肄程!

還是一致性的問題,這個zookeeper用了ZAB共識算法來保證各個zookeeper節(jié)點的一致性选浑。

3. 怎樣使用Zookeeper

zookeeper的啟動需要配置如下的信息(本文以docker啟動)蓝厌,太坑了,這里竟然不能用代碼古徒。


從上圖可以看出ZOO_MY_ID為每個zookeeper的唯一id號拓提,ZOO_SERVERS為集群的ip及端口。當zookeeper起來后隧膘,可以直接進入zookeeper所在的bin目錄代态,查找zkCli.sh寺惫。通過該可執(zhí)行腳本可以找到注冊在zookeeper上的服務(wù)。zkCli.sh所在目錄如下圖所示:

執(zhí)行該腳本后蹦疑,進入zkCli的控制臺西雀,在該控制臺可以查看注冊到zookeeper的服務(wù)。本例以kafka來舉例:

可以到brokers目錄下查看注冊的kafka節(jié)點數(shù)目歉摧。

從上圖中艇肴,可以看到注冊到zookeeper的kafka有四個,id分別為0,1,2,3叁温。其中0的注冊信息可以通過 get /brokers/ids/0來獲得再悼。

各個字段的含義如下:

czxid.節(jié)點創(chuàng)建時的zxid.mzxid.節(jié)點最新一次更新發(fā)生時的

zxid.ctime.節(jié)點創(chuàng)建時的時間戳.

mtime.節(jié)點最新一次更新發(fā)生時的時間戳.

dataVersion.節(jié)點數(shù)據(jù)的更新次數(shù).

cversion.其子節(jié)點的更新次數(shù).

aclVersion.節(jié)點ACL(授權(quán)信息)的更新次數(shù).

ephemeralOwner.如果該節(jié)點為ephemeral節(jié)點,ephemeralOwner值表示與該節(jié)點綁定的sessionid.如果該節(jié)點不是ephemeral節(jié)點,ephemeralOwner值為0.

dataLength.節(jié)點數(shù)據(jù)的字節(jié)數(shù).

numChildren.子節(jié)點個數(shù).


關(guān)于zxid的定義:ZooKeeper狀態(tài)的每一次改變, 都對應(yīng)著一個遞增的Transaction id, 該id稱為zxid. 由于zxid的遞增性質(zhì), 如果zxid1小于zxid2, 那么zxid1肯定先于zxid2發(fā)生. 創(chuàng)建任意節(jié)點, 或者更新任意節(jié)點的數(shù)據(jù), 或者刪除任意節(jié)點, 都會導(dǎo)致Zookeeper狀態(tài)發(fā)生改變, 從而導(dǎo)致zxid的值增加.

再舉個例子,下圖是kafka節(jié)點創(chuàng)建的mytopic膝但,可以看到在0號分區(qū)的kafka主節(jié)點是0號冲九,isr分別同步到0,1跟束,2節(jié)點娘侍。而且通過dataVersion可以看到改變了11次,說明發(fā)了11條消息泳炉。



Kafka的原理

1. Kafka是什么

Kafka是一種分布式的,基于發(fā)布/訂閱的消息系統(tǒng)嚎杨。為什么要用的消息系統(tǒng)呢花鹅?因為利用消息系統(tǒng)有如下的好處:

a)? ? 系統(tǒng)解耦。系統(tǒng)解耦帶來的好處就是擴展性增強枫浙。

b)? ? 事件分發(fā)刨肃。這樣做的好處就是帶來了異步通信,不用某個模塊等待另外一個模塊箩帚,而是將消息發(fā)送過去就不用管了真友,或者消費者只管去拉消息。

c)? ? 消息回溯紧帕。舉個簡單的例子盔然,在玩游戲的過程中,想要做視頻回放是嗜,那么消息系統(tǒng)里做一次記錄即可愈案。開個不是玩笑的玩笑,現(xiàn)在很多人拿kafka當數(shù)據(jù)庫來用鹅搪。簡單方便站绪。

d) ????......

2. 為什么要用到Kafka

a)????快速持久化,可以在O(1)的系統(tǒng)開銷下進行消息持久化丽柿。這個經(jīng)過本人的驗證恢准,的確太不可思議了魂挂,非常快馁筐,源于kafka良好的順序?qū)懩J健?/p>

b)????高吞吐涂召,我自己測的tps可以達到幾十萬;

c)? ? 同時支持單播與廣播眯漩。同一個topic的數(shù)據(jù)芹扭,會廣播給不同的group;同一個group中的worker赦抖,只有一個worker能拿到這個數(shù)據(jù)

d)????支持存儲舱卡。很多人把kafka當數(shù)據(jù)庫來存儲東西。

e)? ? 支持分布式存儲队萤。kafka可以和其他的kafka節(jié)點形成kafka集群轮锥,通過kafka的isr模式,topic的分區(qū)可以分布于不同的節(jié)點要尔。

f)? ? ......

3. 怎樣使用Kafka

先介紹一下kafka的相關(guān)概念舍杜。

????Broker:指服務(wù)于Kafka的一個節(jié)點。

????topic是一個邏輯概念赵辕,用于保證Producer以及Consumer能夠通過該標示進行對接既绩。

????partition是消息的真實存放者。partition會實際存儲在系統(tǒng)的某個目錄还惠。它Topic的一個子概念饲握,

????一個topic可具有多個partition,但Partition一定屬于一個topic蚕键。


下列是一個kafka集群救欧,從下圖可以看出一共有四個節(jié)點,分別為Broker1, Broker2, Broker3, Broker4. 該集群一共有一個topic锣光,該topic供有三個partition笆怠,分別為part0, part1, part2。其中part0分別存儲在Broker1, Broker2, Broker3上誊爹。而part1分別存儲在Broker2, Broker3, Broker4蹬刷。part2分半存儲在Broker1, Broker2, Broker4中。part0的三個Broker中频丘,Broker1為主節(jié)點箍铭。part1的主節(jié)點為Broker2, part2的主節(jié)點為Broker4。三個partition均勻分布椎镣。



需要的環(huán)境:

docker--為啥需要這個呢诈火,因為可以很容易的模擬多機部署,當然如果你是土豪,可以忽略這個冷守,安裝步驟在這里刀崖,當然你也可以參考別的文檔來安裝docker及docker-compose




1. 啟動kafka和zookeeper節(jié)點

利用下面的docker-compose.yml來啟動kafka與zookeeper,下面配置文件里啟動了三個zookeeper和4個kafka節(jié)點拍摇,三個zookeeper組成了一個zookeeper集群亮钦,管理kafka節(jié)點。

三個zookeeper節(jié)點分別為zookeeper0充活,zookeeper1蜂莉,zookeeper2

四個kafka節(jié)點分別為kafka0,kafka1混卵,kafka2映穗,kafka3

我的zookeeper節(jié)點是基于hyperledger/fabric-zookeeper的docker鏡像來啟動的,可以到zookeeper鏡像地址下載幕随。而kafka節(jié)點是基于hyperledger/fabric-kafka的docker鏡像來啟動的蚁滋,可以到kafka鏡像地址下載。

拷貝下面配置文件赘淮,并保存到docker-compose.yml文件中辕录。



在docker-compose.yml所在的目錄中,運行命令docker-compose up -d 命令來啟動容器梢卸。

創(chuàng)建完成后走诞,可以進入zookeeper容器檢查kafka節(jié)點是否都已經(jīng)注冊成功。

運行docker ps命令蛤高,列舉出所有的容器速梗,如下:


進入其中的一個zookeeper容器,通過如下命令


運行zkCli.sh命令襟齿,來檢查kafka節(jié)點有沒有注冊到zookeeper上。



檢查其中的一個broker id 如下:


從中可以知道brokerid 0,1,2,3都已經(jīng)注冊到zookeeper集群上了枕赵,而詳細brokerid 0的信息中可以得到其ip猜欺,端口等等。

具體kafka在zookeeper上的注冊消息圖如下拷窜,詳細我找到了一個網(wǎng)頁 开皿,可以參考


2. 創(chuàng)建topic

進入kafka節(jié)點,利用下述命令


運行下述命令篮昧,創(chuàng)建mytopic赋荆,該topic有一個分區(qū),部署有三個副本懊昨。

可以進入zookeeper節(jié)點窄潭,用zkCli.sh查看topic下的信息如下。


從中可以看出broker3為主節(jié)點酵颁,總共有3個副本嫉你,分別是broker0,broker1,broker3

3. 發(fā)送消息

進入kafka容器月帝,利用該kafka自帶腳本可以發(fā)送消息,如下即向本kafka節(jié)點的mytopic發(fā)送消息

4. 消費消息

進入kafka容器幽污,利用kafka自帶腳本嚷辅,可以對消息進行消費,如下即向kafka節(jié)點消費消息

到zookeeper中距误,啟動zkCli.sh可以看到簸搞,消費者是在zookeeper中注冊了消費者id,這樣可以保障group單播准潭。



本文參考:

https://www.cnblogs.com/wuxl360/p/5817471.html

http://blog.csdn.net/lizhitao/article/details/51718185

http://blog.csdn.net/lizhitao/article/details/23744675

http://blog.csdn.net/eric_sunah/article/details/46891901

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
  • 序言:七十年代末趁俊,一起剝皮案震驚了整個濱河市,隨后出現(xiàn)的幾起案子惋鹅,更是在濱河造成了極大的恐慌则酝,老刑警劉巖,帶你破解...
    沈念sama閱讀 218,858評論 6 508
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件闰集,死亡現(xiàn)場離奇詭異沽讹,居然都是意外死亡,警方通過查閱死者的電腦和手機武鲁,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 93,372評論 3 395
  • 文/潘曉璐 我一進店門爽雄,熙熙樓的掌柜王于貴愁眉苦臉地迎上來,“玉大人沐鼠,你說我怎么就攤上這事挚瘟。” “怎么了饲梭?”我有些...
    開封第一講書人閱讀 165,282評論 0 356
  • 文/不壞的土叔 我叫張陵乘盖,是天一觀的道長。 經(jīng)常有香客問我憔涉,道長订框,這世上最難降的妖魔是什么? 我笑而不...
    開封第一講書人閱讀 58,842評論 1 295
  • 正文 為了忘掉前任兜叨,我火速辦了婚禮穿扳,結(jié)果婚禮上,老公的妹妹穿的比我還像新娘国旷。我一直安慰自己矛物,他們只是感情好,可當我...
    茶點故事閱讀 67,857評論 6 392
  • 文/花漫 我一把揭開白布跪但。 她就那樣靜靜地躺著履羞,像睡著了一般。 火紅的嫁衣襯著肌膚如雪。 梳的紋絲不亂的頭發(fā)上吧雹,一...
    開封第一講書人閱讀 51,679評論 1 305
  • 那天骨杂,我揣著相機與錄音,去河邊找鬼雄卷。 笑死搓蚪,一個胖子當著我的面吹牛,可吹牛的內(nèi)容都是我干的丁鹉。 我是一名探鬼主播妒潭,決...
    沈念sama閱讀 40,406評論 3 418
  • 文/蒼蘭香墨 我猛地睜開眼,長吁一口氣:“原來是場噩夢啊……” “哼揣钦!你這毒婦竟也來了雳灾?” 一聲冷哼從身側(cè)響起,我...
    開封第一講書人閱讀 39,311評論 0 276
  • 序言:老撾萬榮一對情侶失蹤冯凹,失蹤者是張志新(化名)和其女友劉穎谎亩,沒想到半個月后,有當?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體宇姚,經(jīng)...
    沈念sama閱讀 45,767評論 1 315
  • 正文 獨居荒郊野嶺守林人離奇死亡匈庭,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點故事閱讀 37,945評論 3 336
  • 正文 我和宋清朗相戀三年,在試婚紗的時候發(fā)現(xiàn)自己被綠了浑劳。 大學(xué)時的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片阱持。...
    茶點故事閱讀 40,090評論 1 350
  • 序言:一個原本活蹦亂跳的男人離奇死亡,死狀恐怖魔熏,靈堂內(nèi)的尸體忽然破棺而出衷咽,到底是詐尸還是另有隱情,我是刑警寧澤蒜绽,帶...
    沈念sama閱讀 35,785評論 5 346
  • 正文 年R本政府宣布镶骗,位于F島的核電站,受9級特大地震影響躲雅,放射性物質(zhì)發(fā)生泄漏鼎姊。R本人自食惡果不足惜,卻給世界環(huán)境...
    茶點故事閱讀 41,420評論 3 331
  • 文/蒙蒙 一吏夯、第九天 我趴在偏房一處隱蔽的房頂上張望。 院中可真熱鬧即横,春花似錦噪生、人聲如沸。這莊子的主人今日做“春日...
    開封第一講書人閱讀 31,988評論 0 22
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽。三九已至,卻和暖如春桨嫁,著一層夾襖步出監(jiān)牢的瞬間植兰,已是汗流浹背。 一陣腳步聲響...
    開封第一講書人閱讀 33,101評論 1 271
  • 我被黑心中介騙來泰國打工璃吧, 沒想到剛下飛機就差點兒被人妖公主榨干…… 1. 我叫王不留楣导,地道東北人。 一個月前我還...
    沈念sama閱讀 48,298評論 3 372
  • 正文 我出身青樓畜挨,卻偏偏與公主長得像筒繁,于是被迫代替她去往敵國和親。 傳聞我的和親對象是個殘疾皇子巴元,可洞房花燭夜當晚...
    茶點故事閱讀 45,033評論 2 355

推薦閱讀更多精彩內(nèi)容