Kafka消息模型


一、消息傳遞模型

   傳統的消息隊列最少提供兩種消息模型,一種P2P,一種PUB/SUB,而Kafka並沒有這么做,巧妙的,它提供了一個消費者組的概念,一個消息可以被多個消費者組消費,但是只能被一個消費者組里的一個消費者消費,這樣當只有一個消費者組時就等同與P2P模型,當存在多個消費者組時就是PUB/SUB模型。

  Kafka 的 consumer 是以pull的形式獲取消息數據的。 pruducer push消息到kafka cluster ,consumer從集群中pull消息,如下圖。該博客主要講解. Parts在消費者中的分配、以及相關的消費者順序、底層結構元數據信息、Kafka數據讀取和存儲等。

二、消息持久化

   很多系統、組件為了提升效率一般恨不得把所有數據都扔到內存里,然后定期flush到磁盤上;可實際上,現代操作系統也是這樣,所有的現代操作系統都樂於將空閑內存轉作磁盤緩存(頁面緩存),想不用都難;對於這樣的系統,他的數據在內存中保存了一份,同時也在OS的頁面緩存中保存了一份,這樣不但多了一個步驟還讓內存的使用率下降了一半;因此,Kafka決定直接使用頁面緩存;但是隨機寫入的效率很慢,為了維護彼此的關系順序還需要額外的操作和存儲,而線性的寫入可以避免這些,實際上,線性寫入(linear write)的速度大約是300MB/秒,但隨即寫入卻只有50k/秒,其中的差別接近10000倍。這樣,Kafka以頁面緩存為中間的設計在保證效率的同時還提供了消息的持久化,每個消費者自己維護當前讀取數據的offser(也可委托給zookeeper),以此可同時支持在線和離線的消費。

三、Push vs. Pull

  對於消息的消費,ActiveMQ使用PUSH模型,而Kafka使用PULL模型,兩者各有利弊,對於PUSH,broker很難控制數據發送給不同消費者的速度,而PULL可以由消費者自己控制,但是PULL模型可能造成消費者在沒有消息的情況下盲等,這種情況下可以通過long polling機制緩解,而對於幾乎每時每刻都有消息傳遞的流式系統,這種影響可以忽略。

四、消息投遞可靠性

  一個消息如何算投遞成功,Kafka提供了三種模式:

  • 第一種是啥都不管,發送出去就當作成功,這種情況當然不能保證消息成功投遞到broker;
  • 第二種是Master-Slave模型,只有當Master和所有Slave都接收到消息時,才算投遞成功,這種模型提供了最高的投遞可靠性,但是損傷了性能;
  • 第三種模型,即只要Master確認收到消息就算投遞成功;實際使用時,根據應用特性選擇,絕大多數情況下都會中和可靠性和性能選擇第三種模型

   消息在broker上的可靠性,因為消息會持久化到磁盤上,所以如果正常stop一個broker,其上的數據不會丟失;但是如果不正常stop,可能會使存在頁面緩存來不及寫入磁盤的消息丟失,這可以通過配置flush頁面緩存的周期、閾值緩解,但是同樣會頻繁的寫磁盤會影響性能,又是一個選擇題,根據實際情況配置。

   消息消費的可靠性,Kafka提供的是“At least once”模型,因為消息的讀取進度由offset提供,offset可以由消費者自己維護也可以維護在zookeeper里,但是當消息消費后consumer掛掉,offset沒有即時寫回,就有可能發生重復讀的情況,這種情況同樣可以通過調整commit offset周期、閾值緩解,甚至消費者自己把消費和commit offset做成一個事務解決,但是如果你的應用不在乎重復消費,那就干脆不要解決,以換取最大的性能。


免責聲明!

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



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