什么時候該用RabbitMQ ,什么時候該用 Apache Kafka
人類如何做出決策? 在日常生活中,情感總是短路因素,導致在復雜或壓倒性的決定上扣動扳機。但對于做有長期影響,復雜決策,的表意識,不可能是純粹的沖動。高性能的人通常使用斷路器,“本能,” “直覺,” 或其他的情緒,只有一次他們的表意識,潛意識吸收了作出決定所需的所有事實。
今天有很多的消息傳遞技術(shù), 數(shù)不清的 ESBs, 和近100 iPaaS供應商在市場上。 自然,這導致了有關(guān)如何為您的需要-特別是那些已經(jīng)投資在一個特定的選擇,選擇正確的消息傳遞技術(shù)的問題 。我們批發(fā)選擇嗎? 用正確的工具做正確的工作?我們有沒有正確地布置手頭的工作以滿足業(yè)務需求? 鑒于此,對我來說,合適的工具是什么? 更糟糕的是,詳盡的市場分析可能永遠無法完成,但由于集成代碼的平均壽命,盡職調(diào)查是至關(guān)重要的。
這篇文章致力于給予潛意識,表意識 一些公平的考慮,從今天最現(xiàn)代,最受歡迎的選擇: RabbitMQ和Apache Kafka。 每個都有自己的起源故事, 設計意圖,使用案例,被應用, 整合能力,和開發(fā)人員的經(jīng)驗。對于任何的軟件,起源揭示總體設計意圖,都是一個很好的起點。
起源
RabbitMQ 是一個 “傳統(tǒng)的” 消息代理,實現(xiàn)多種消息傳遞協(xié)議。 是第一個開源消息代理,達到合理的功能水平, 客戶端庫,開發(fā)工具,和質(zhì)量文檔。 RabbitMQ 最初開發(fā)來實現(xiàn)AMQP,具有強大路由功能的消息傳遞的開放式路由協(xié)議。盡管Java有消息傳遞標準像JMS,但對需要傳遞消息的分布式非java應用沒有幫助,這嚴重限制了很多集成方案,微服務或單組件。隨著AMQP的到來,跨語言的靈活性,成為真正的開源消息代理。
Apache Kafka是用Scala開發(fā)的,起初應用于 LinkedIn ,作為一種簡化Hadoop 從 Apache Flume提取消息的方案。 從復數(shù)數(shù)據(jù)源消費和生產(chǎn)的數(shù)據(jù),為每個源和目標配對編寫獨立的數(shù)據(jù)管道。Kafka 幫助 LinkedIn 標準化數(shù)據(jù)管道并允許將數(shù)據(jù)從每個系統(tǒng)中取出一次并存入每個系統(tǒng)一次,使管道 (和操作) 更簡單。Kafka是如今Apache Software軟件基金會的通用配置。特別地,很好的與Apache Zookeeper集成,形成了Kafka分布式分區(qū)的支柱。 許多人認為 Zookeeper的需求并不是那么高,它賦予了Kafka用戶集群的益處。
體系結(jié)構(gòu)和設計
RabbitMQ i被設計為通用消息代理,采用點對點的幾種變化, 請求/答復,和發(fā)布-訂閱通信風格模式。它使用智能代理/啞消費者模型,專注于消息傳遞消費者的一致性,作為代理跟蹤消費者的狀態(tài),保證以大致相同的速度消費。配置正確時表現(xiàn)良好,成熟,被支持的很好 (客戶端庫包括 Java, .NET, node.js, Ruby, PHP和很多其他語言),有幾十個插件可用,將其擴展到更多用例和集成場景。
簡化的整體 RabbitMQ 體系結(jié)構(gòu)(source).
RabbitMQ的通信,根據(jù)需要可以是同步或異步。推送者發(fā)送消息到交換區(qū),消費者從隊列檢索消息。 通過發(fā)送消息到交換區(qū)的形式,將生產(chǎn)者解耦,確保生產(chǎn)者不承擔硬編碼路由壓力。 RabbitMQ 還提供了一些分布式部署方案 (要求所有節(jié)點可以解析主機名)。它可以設置為多節(jié)點集群為集群聯(lián)盟,并且不依賴外部服務 (但一些集群形成插件可以使用AWS APIs, DNS, Consul,等)。
Apache Kafka 是專為高容量發(fā)布-訂閱消息流設計的,意味著經(jīng)久耐用, 快速,而且可擴展的。在其本質(zhì)上, Kafka 提供持久的消息存儲,在某些方面類似于數(shù)據(jù)庫,在服務器集群中運行,存儲流記錄的類別稱為主題。
全局 Apache Kafka 體系結(jié)構(gòu)(1 主題, 1 分區(qū), 4 復制因子). (source)
每條消息包含一個鍵,一個值和一個時間戳。 同RabbitMQ幾乎相反, Kafka使用了笨代理, 并使用智能消費者讀取其緩沖區(qū)。 Kafka不嘗試跟蹤那些被消費者消費的消息,只保留未讀消息;相反, Kafka保留所有消息的一組時間,消費者負責跟蹤他們在每個日志的位置 (消費狀態(tài))。 因此,用正確的開發(fā)者人才 創(chuàng)建消費者代碼, Kafka 可以支持大量的消費者并且保留大量數(shù)據(jù)以很少的開銷。如上圖所示,Kafka確實需要外部服務運行 – 在這種情況下,Apache Zookeeper, 通常被認為是必要,理解,設置,和操作的。
需求和用例
許多開發(fā)人員開始探索消息傳遞,當他們意識到他們必須把很多東西連接在一起,和其他集成模式,如共享數(shù)據(jù)庫是不可行的或太危險的時候。
Apache Kafka 將其描述為分布式流媒體平臺,但更為人知的是一個持久的存儲庫,有著很好的Hadoop/Spark 支持。文檔做得很好,討論流行的用例,比如網(wǎng)站活動跟蹤,指標,日志聚合,流處理,事件溯源和提交日志。這些用例之一,它描述了消息,可能產(chǎn)生一些混亂。 所以讓我們打開一點,看的更清晰,關(guān)于哪種消息方案更適合Kafka,比如:
- 從A到B的流沒有復雜的路由, 有最大吞吐量(100k/sec+),按分區(qū)順序交付至少一次。
- 當你的應用程序需要訪問流歷史,按分區(qū)順序交付至少一次。Kafka是持久的消息存儲和客戶可以得到一個 “replay” 事件流的需求,相對于更傳統(tǒng)的消息代理,一旦一個消息被交付,就會從隊列中移除。
- 當你有聰明的消費者,能可靠地跟蹤他們的日志偏移。
- 如果您的應用程序需要 “無限的” 隊列。
RabbitMQ是一個通用消息傳遞解決方案,通常用于, 當用戶等待結(jié)果時,允許web服務器快速響應請求,而不是被迫執(zhí)行重資源程序。也有利于分發(fā)消息到多個消費者進行消費, 或在高負荷條件下平衡worker之間的荷載 (20k+/sec)。當你的需求超越吞吐量, RabbitMQ有很多提供: 特性,可靠消息傳遞, 路由,聯(lián)合會, HA, 安全, 管理工具和其他特性。讓我們看看一些最適合RabbitMQ的場景,比如:
- 您的應用程序需要,與現(xiàn)有協(xié)議組合,比如AMQP 0-9-1, STOMP, MQTT, AMQP 1.0.
- 你需要成熟,容易理解的一致性保證,為您的信息傳遞。
- 你的應用需要多種類型的點對點協(xié)議,請求/應答,和發(fā)布/訂閱 消息.
- 復雜的消費者路由,整合多個服務/應用程序,使用難以掌握的路由邏輯。
- 當與你現(xiàn)有的 IT 基礎設施整合很重要, RabbitMQ 更好。
RabbitMQ 也可以有效地解決幾個上面的Kafka強有力的用例,但要借助額外的軟件。RabbitMQ經(jīng)常與Apache Cassandra配合使用,當應用程序需要訪問流歷史時,或與LevelDB插件,對于應用程序需要 “無限” 隊列, 但都不是RabbitMQ自帶的。
開發(fā)經(jīng)驗
RabbitMQ正式支持Java, Spring, .NET, PHP, Python, Ruby, JavaScript, Go, Elixir, Objective-C, Swift – 與許多其他 客戶和開發(fā)工具,通過社區(qū)插件。RabbitMQ 客戶端庫是成熟且良好文檔的。
Apache Kafka 在這一領(lǐng)域已經(jīng)取得了長足進步,雖然他主要是Java客戶端,有越來越多的社區(qū)目錄 開放源碼客戶端, 生態(tài)系統(tǒng)項目,以及作為適配器 SDK 允許您建立自己的系統(tǒng)集成。大部分的配置已經(jīng)設定好了,通過.properties 文件或編程方式。
這兩個選項的流行,在許多其他軟件供應商,有很強的影響力,確保RabbitMQ 和Kafka正常工作,通過他們的技術(shù)。
安全和操作
安全和操作都是RabbitMQ的強項。 RabbitMQ管理插件提供了HTTP API,一個基于瀏覽器的 UI 用于管理和監(jiān)控,加上CLI工具給予操作員。 外部工具,如果長期監(jiān)測數(shù)據(jù)存儲,比如CollectD, Datadog或者New Relic也是需要的。 RabbitMQ還提供了API和監(jiān)控工具,審核和應用故障排除。除了支持TLS,RabbitMQ附帶RBAC支持通過內(nèi)置數(shù)據(jù)存儲, LDAP或外部基于HTTPS的供應商,并支持身份驗證使用x509證書,代替用戶名/密碼對。額外的身份驗證方法 可以使用插件相當直接地擴展。
這些領(lǐng)域?qū)pache Kafka.構(gòu)成了挑戰(zhàn)。在安全方面,最近的Kafka 0.9版本附加了TLS,,JAAS基于角色的訪問控制,Kerberos/plain/scram認證,使用CLI管理安全策略。 這使得早期版本大幅改善,當時您只能在網(wǎng)絡級別鎖定訪問權(quán)限,對于共享或多用戶,這不起作用。
Kafka使用管理CLI由shell腳本、 屬性文件組成,特別是格式化JSON文件。 Kafka 經(jīng)紀人,生產(chǎn)者,和消費者排放指標 通過Yammer / JMX,但不維護任何歷史,這實際意味著使用第三方監(jiān)測系統(tǒng)。使用這些工具,操作能夠管理分區(qū)和主題,檢查消費者偏移位置,與使用Apache Zookeeper為Kafka提供的HA和FT功能。例如,一個3節(jié)點Kafka 集群 即使兩個節(jié)點失敗也能提供功能。然而,如果你想支持Zookeeper最大數(shù)目的失敗,你需要額外的5個Zookeeper節(jié)點 ,Zookeeper是基于法定人數(shù)的系統(tǒng),只能容忍 N/2+1的失敗。這明顯的不應該共存與Kafka節(jié)點 – 因此,要建立的3節(jié)點卡夫卡系統(tǒng),您需要大約八臺服務器。 運營商當推理任何卡夫卡系統(tǒng)的可用性時,考慮到ZK集群屬性,無論是資源消耗還是設計。
性能
Kafka照以下設計:100k/sec性能往往是人們選擇 Apache Kafka的關(guān)鍵驅(qū)動力。它的實現(xiàn)很大依賴開發(fā)者能夠?qū)懗雎斆鞯南M者代碼。
當然,每秒消息速率是很難狀態(tài)和量化,因為他們依賴很多,包括你的環(huán)境和硬件,工作負載的性質(zhì),使用哪種交貨保證 (e.g. 持久性是昂貴的,鏡像更是如此), etc.
20K/sec是很容易使用一個Rabbit隊列實現(xiàn)的, 事實上跟多一些也不是很難,只要沒有太多要求的擔保。隊列的支持,通過一個, 在本地操作系統(tǒng)線程池上進行協(xié)作調(diào)度的,輕量級的Erlang線程 – 因此,它自然成為了單隊列的關(guān)鍵點或瓶頸,永遠不會做比CPU周期內(nèi)能得到的更多的工作。
增加信息秒速率通常歸結(jié)為妥善利用可用的并行性環(huán)境,通過諸如通過聰明的路由打破交通跨多個隊列 (從而可以同時運行不同的隊列)。當RabbitMQ實現(xiàn)一百萬每秒的消息傳遞, 它通常會明智的慢下來 – 但通過使用大量的資源,周圍 30 RabbitMQ節(jié)點。 大多數(shù)RabbitMQ使用者享受由三到七個RabbitMQ節(jié)點提供的高性能。
Making the Call
市場上的其他高級選項的一些研究。如果你想深入與最流行的選擇,查看 Nicolas Nannoni碩士論文 ,它獨具特色的一面,比較表在4.4節(jié) (page 39) 兩年后仍然相當準確 – 值得一讀。
在研究時,盡可能形成涉眾和業(yè)務的循環(huán)。理解商業(yè)用例是為你的情況做出正確的選擇的最大的單因素 。 然后, 如果你是流行技術(shù)粉,你最好的辦法就是睡在上面, 讓它滲透,讓你的本能接管。 你就明白了。