一、介紹
1. 消息中間件的定義
沒有標準定義,一般認爲,採用消息傳送機制/消息隊列 的中間件技術,進行數據交流,用在分佈式系統的集成
2. 爲什麼要用消息中間件
解決分佈式系統之間消息的傳遞,用戶下單減庫存,調用物流系統。隨着業務量的增大,需要對系統進行拆分(服務化和業務拆分),拆分後的系統之間的交互一般用RPC(遠程過程調用)。如果系統擴充到有幾十個接口,就需要用消息中間件來解決問題
3. 消息中間件和RPC有什麼區別
3.1 功能特點:
在架構上,RPC和Message的差異點:Message有一箇中間結點Message Queue,可以把消息存儲。
3.2 消息的特點
Message Queue把請求的壓力保存一下,逐漸釋放出來,讓處理者按照自己的節奏來處理。
Message Queue引入一下新的結點,讓系統的可靠性會受Message Queue結點的影響。
Message Queue是異步單向的消息。發送消息設計成是不需要等待消息處理的完成。
所以對於有同步返回需求,用Message Queue則變得麻煩了。
3.3 RPC的特點
同步調用,對於要等待返回結果/處理結果的場景,RPC是可以非常自然直覺的使用方式。
# RPC也可以是異步調用。
由於等待結果,Consumer(Client)會有線程消耗。
如果以異步RPC的方式使用,Consumer(Client)線程消耗可以去掉。但不能做到像消息一樣暫存消息/請求,壓力會直接傳導到服務Provider。
3.4 適用場合說明
希望同步得到結果的場合,RPC合適。
希望使用簡單,則RPC;RPC操作基於接口,使用簡單,使用方式模擬本地調用。異步的方式編程比較複雜。
不希望發送端(RPC Consumer、Message Sender)受限於處理端(RPC Provider、Message Receiver)的速度時,使用Message Queue。
隨着業務增長,有的處理端處理量會成爲瓶頸,會進行同步調用到異步消息的改造。
這樣的改造實際上有調整業務的使用方式。
比如原來一個操作頁面提交後就下一個頁面會看到處理結果;改造後異步消息後,下一個頁面就會變成“操作已提交,完成後會得到通知”。
4. 消息中間件的使用場景
4.1 異步處理
用戶註冊(50ms),還需發送郵件(50ms)和短信(50ms)
串行:(150ms)用戶註冊—》發送郵件----》發送短信
並行(100ms):用戶註冊—》發送郵件----》發送短信
消息中間件(56ms):
用戶註冊(50ms)—》(6ms)消息中間件《-----發送郵件《-----發送短信
說明:
用戶註冊時,可能還需要同時發送郵件和短信,使用串行的方式進行處理時花費的時間比較久;這時就會考慮並行處理,即用戶註冊完以後,同時啓動兩個兩個線程去發送郵件和短信,這樣時間就會花費得更少。
如果引入消息中間件的話就會比並行處理更快,即用戶註冊時,把註冊信息放到消息中間件裏面,然後發送郵件和短信的程序自己去消息中間件裏面那用戶註冊的消息來消費
4.2 應用的解耦
訂單系統---》庫存系統(強耦合)
消息中間件:訂單系統---》消息中間件《----庫存系統(解耦)
原因:下訂單以後還要同步去修改庫存,沒有必要耦合在一起
說明:
用戶下訂單時,可能還需要去更新庫存,這個時候下訂單的後,還需要同步去更新庫存,這樣兩個系統之間就會有很強的耦合。
所以這個時候引入消息中間件,當用戶下訂單後,直接把訂單信息放入消息中間件裏面,接着就不用管了,庫存系統直接去消息中間件裏面那訂單信息來消費就行了,這樣訂單系統和庫存系統之間就解耦了
4.3 流量的削峯
用戶請求-----》秒殺應用
應用的前端加入消息隊列
用戶請求-----》消息隊列《----秒殺應用
原因:用戶訪問太多,服務器承受不了
說明:
在做秒殺的時候會有許多訪問,可能導致系統承受不住。這個時候就需要在應用的前端加入消息隊列,然後秒殺系統就可以直接去消息隊列裏面拿消息來消費就行了,秒殺系統是可以選擇性的拿消息過來消費的,如果消息太多就會選擇性的丟棄一些消息
4.4 日誌處理
錯誤日誌---》消息隊列《----日誌處理
用戶行爲日誌--》消息隊列(kafka)《-----日誌的存儲或流式處理
原因:機器太多,日誌查看不方便
說明:
當系統太多的時候,部署了很多機器,每臺機器上面都有日誌,定位問題的時候不可能去每一臺機器去看日誌。
這個時候就需要引入消息中間件,把所有的日誌放到消息中間件裏面,然後在通過一個應用去讀取日誌存庫或者展示
4.5 純粹的消息通信
點對點通信
5. 常見消息中間件比較
說明:
kafka和RabbitMQ的比較
1)RabbitMq比kafka成熟,在可用性上,穩定性上,可靠性上,RabbitMq超過kafka
2)Kafka設計的初衷就是處理日誌的,可以看做是一個日誌系統,針對性很強,所以它並沒有具備一個成熟MQ應該具備的特性
3)Kafka的性能(吞吐量、tps)比RabbitMq要強
二、JMS規範
1. 什麼是JMS規範
JMS(Java Messaging Service)規範,本質是API,Java平臺消息中間件的規範,java應用程序之間進行消息交換。並且通過提供標準的產生、發送、接收消息的接口簡化企業應用的開發。對應的實現ActiveMQ
2. JMS對象模型包含如下幾個要素
1)連接工廠:創建一個JMS連接
2)JMS連接:客戶端和服務器之間的一個連接。
3)JMS會話:客戶端和服務器會話的狀態,建立在連接之上的
4)JMS目的:消息隊列
5)JMS生產者:消息的生成
6)JMS消費者:接收和消費消息
7)Broker:消息中間件的實例(ActiveMQ)
3. JMS規範中的點對點模式
隊列,一個消息只有一個消費者(即使有多個接受者監聽隊列),消費者是要向隊列應答成功
4. JMS規範中的主題模式(發佈訂閱)
發佈到Topic的消息會被當前主題所有的訂閱者消費
5. JMS規範中的消息類型
TextMessage,MapMessage,ObjectMessage,BytesMessage,StreamMessage
三、ActiveMQ、RabbitMQ、RocketMQ、Kafka之間的比較
特性 |
ActiveMQ |
RabbitMQ |
RocketMQ |
Kafka |
單機吞吐量 |
萬級,吞吐量比RocketMQ和Kafka要低了一個數量級 |
萬級,吞吐量比RocketMQ和Kafka要低了一個數量級 |
十萬級,RocketMQ也是可以支撐高吞吐的一種MQ |
十萬級別,這是kafka最大的優點,吞吐量高。一般配合大數據類的系統來進行實時數據計算、日誌採集 |
topic數量對吞吐量的影響 |
|
|
topic可以達到幾百,幾千個的級別,吞吐量會有較小幅度的下降 這是RocketMQ的一大優勢,在同等機器下,可以支撐大量的topic |
topic從幾十個到幾百個的時候,吞吐量會大幅度下降 在同等機器下,kafka儘量保證topic數量不要過多。如果要支撐大規模topic,需要增加更多的機器資源 |
時效性 |
ms級 |
微秒級,延遲最低 |
ms級 |
延遲在ms級以內 |
可用性 |
高,基於主從架構實現高可用性 |
高,基於主從架構實現高可用性 |
非常高,分佈式架構 |
非常高,kafka是分佈式的,一個數據多個副本,少數機器宕機,不會丟失數據,不會導致不可用 |
消息可靠性 |
有較低概率丟失數據 |
|
經過參數優化配置,可以做到0丟失 |
經過參數優化配置,可以做到0丟失 |
功能支持 |
MQ領域的功能極其完備 |
基於erlang開發,所以併發能力很強,性能極其好,延時很低 |
MQ功能較爲完善,還是分佈式的,擴展性好 |
功能較爲簡單,支持簡單的MQ功能,在大數據領域的實時計算以及日誌採集被大規模使用 |
優劣勢總結 |
非常成熟,功能強大,在業內大量的公司以及項目中都有應用。 缺點: 偶爾會有較低概率丟失消息,而且現在社區以及國內應用都越來越少,官方社區現在維護越來越少,幾個月才發佈一個版本; 主要是基於解耦和異步來用的,較少在大規模吞吐的場景中使用。
|
erlang語言開發,性能極其好,延時很低; 吞吐量到萬級,MQ功能比較完備; 開源提供的管理界面非常棒,很好用; 社區相對比較活躍,幾乎每個月都發布幾個版本; 在國內一些互聯網公司近幾年用rabbitmq也比較多。 缺點: RabbitMQ吞吐量會低一些,這是因爲他做的實現機制比較重。 因爲是基於erlang開發,很難去看懂源碼,難以定製和掌控,基本職能依賴於開源社區的快速維護和修復bug。 |
接口簡單易用,而且畢竟在阿里大規模應用過,有阿里品牌保障; 日處理消息上百億之多,可以做到大規模吞吐,性能也非常好,分佈式擴展也很方便; 社區維護還可以,可靠性和可用性都不錯,還可以支撐大規模的topic數量,支持複雜MQ業務場景; 而且一個很大的優勢在於,阿里出品都是java系的,可以自己閱讀源碼,定製自己公司的MQ,易於定製和掌控。 缺點: 社區活躍度相對較爲一般,不過也還可以,文檔相對來說簡單一些,然後接口這塊不是按照標準JMS規範走的有些系統要遷移需要修改大量代碼; 因爲是阿里出臺的技術,得做好這個技術萬一被拋棄,社區黃掉的風險。 |
kafka的特點其實很明顯,就是僅僅提供較少的核心功能,但是提供超高的吞吐量,ms級的延遲,極高的可用性以及可靠性,而且分佈式可以任意擴展; 同時kafka最好是支撐較少的topic數量即可,保證其超高吞吐量; 缺點: kafka唯一的一點劣勢是有可能消息重複消費,那麼對數據準確性會造成極其輕微的影響,在大數據領域中以及日誌採集中,這點輕微影響可以忽略,這個特性天然適合大數據實時計算以及日誌收集場景。 |