消息中間件概述


什么是消息中間件?

 

消息中間件(MQ)的定義

其實並沒有標准定義。一般認為,消息中間件屬於分布式系統中一個子系統,關注於數據的發送和接收,利用高效可靠的異步消息傳遞機制對分布式系統中的其余各個子系統進行集成。

高效:對於消息的處理處理速度快。

可靠:一般消息中間件都會有消息持久化機制和其他的機制確保消息不丟失。

異步:指發送完一個請求,不需要等待返回,隨時可以再發送下一個請求,既不需要等待。

一句話總結,我們消息中間件不生產消息,只是消息的搬運工。

 

 

 

為什么要用消息中間件?

假設一個電商交易的場景,用戶下單之后調用庫存系統減庫存,然后需要調用物流系統進行發貨,如果交易、庫存、物流是屬於一個系統的,那么就是接口調用。但是隨着系統的發展,各個模塊越來越龐大、業務邏輯越來越復雜,必然是要做服務化和業務拆分的。這個時候就需要考慮這些系統之間如何交互,一般的處理方式就是 RPC(Remote Procedure Call)(具體實現 dubbo,SpringCloud)。系統繼續發展,可能一筆交易后續需要調用幾十個接口來執行業務,比如還有風控系統、短信服務等等。這個時候就需要消息中間件登場來解決問題了。

所以消息中間件主要解決分布式系統之間消息的傳遞,同時為分布式系統中其他子系統提供了松耦合的架構,同時還有以下好處:

 

  低耦合

  低耦合,不管是程序還是模塊之間,使用消息中間件進行間接通信。

 

  異步通信能力

  異步通信能力,使得子系統之間得以充分執行自己的邏輯而無需等待。

 

 

  緩沖能力

  緩沖能力,消息中間件像是一個巨大的蓄水池,將高峰期大量的請求存儲下來慢慢交給后台進行處理,對於秒殺業務來說尤為重要。

 

 

  伸縮性

  伸縮性,是指通過不斷向集群中加入服務器的手段來緩解不斷上升的用戶並發訪問壓力和不斷增長的數據存儲需求。就像彈簧一樣掛東西一樣,用戶多,伸一點,用戶少,淺一點,啊,不對,縮一點。是伸縮,不是深淺。衡量架構是否高伸縮性的主要標准就是是否可用多台服務器構建集群,是否容易向集群中添加新的服務器。加入新的服務器后是否可以提供和原來服務器無差別的服務。集群中可容納的總的服務器數量是否有限制。

 

 

  擴展性

  擴展性,主要標准就是在網站增加新的業務產品時,是否可以實現對現有產品透明無影響,不需要任何改動或者很少改動既有業務功能就可以上線新產品。比如用戶購買電影票的應用,現在我們要增加一個功能,用戶買了鐵血戰士的票后,隨機抽取用戶送異形的限量周邊。怎么做到不改動用戶購票功能的基礎上增加這個功能。熟悉設計模式的同學,應該很眼熟,這是設計模式中的開閉原則(對擴展開放,對修改關閉)在架構層面的一個原則。

 

 

和 RPC 有何區別?

 

RPC 和消息中間件的場景的差異很大程度上在於就是“依賴性”和“同步性”。

依賴性:

 

 

 

 

比如短信通知服務並不是事交易環節必須的,並不影響下單流程,不是強依賴,所以交易系統不應該依賴短信服務。如果是 RPC 調用,短信通知服務掛了,整個業務就掛了,這個就是依賴性導致的,而消息中間件則沒有這個依賴性。

消息中間件出現以后對於交易場景可能是調用庫存中心等強依賴系統執行業務,之后發布一條消息(這條消息存儲於消息中間件中)。像是短信通知服務、數據統計服務等等都是依賴於消息中間件去消費這條消息來完成自己的業務邏輯。

 

同步性:

RPC 方式是典型的同步方式,讓遠程調用像本地調用。消息中間件方式屬於異步方式。

 

 

 

 

相同點:都是分布式下面的通信方式。

 

消息中間件有些什么使用場景?

異步處理

  場景說明:用戶注冊后,需要發注冊郵件和注冊短信。傳統的做法有兩種 1.串行的方式;2.並行方式。

串行方式:將注冊信息寫入數據庫成功后,發送注冊郵件,再發送注冊短信。以上三個任務全部完成后,返回給客戶端。

 

 

 

(2)並行方式:將注冊信息寫入數據庫成功后,發送注冊郵件的同時,發送注冊短信。以上三個任務完成后,返回給客戶端。與串行的差別是,並行的方式可以提高處理的時間。

假設三個業務節點每個使用 50 毫秒鍾,不考慮網絡等其他開銷,則串行方式的時間是 150 毫秒,並行的時間可能是 100 毫秒。

 

小結:如以上案例描述,傳統的方式系統的性能(並發量,吞吐量,響應時間)會有瓶頸。如何解決這個問題呢?

引入消息隊列,將不是必須的業務邏輯,異步處理。

 

 

按照以上約定,用戶的響應時間相當於是注冊信息寫入數據庫的時間,也就是 50 毫秒。注冊郵件,發送短信寫入消息隊列后,直接返回,因此寫入消息隊列的速度很快,基本可以忽略,因此用戶的響應時間可能是 50 毫秒。因此架構改變后,系統的吞吐量提高到每秒 20 QPS。比串行提高了 3 倍,比並行提高了兩倍。

 

應用解耦

場景說明:用戶下單后,訂單系統需要通知庫存系統。傳統的做法是,訂單系統調用庫存系統的接口。

傳統模式的缺點:

 

1 假如庫存系統無法訪問,則訂單減庫存將失敗,從而導致訂單失敗;

2 訂單系統與庫存系統耦合;

 

 

 

 

 

如何解決以上問題呢?引入應用消息隊列后的方案

  訂單系統:用戶下單后,訂單系統完成持久化處理,將消息寫入消息隊列,返回用戶訂單下單成功。

  庫存系統:訂閱下單的消息,采用拉/推的方式,獲取下單信息,庫存系統根據下單信息,進行庫存操作。

 

假如:在下單時庫存系統不能正常使用。也不影響正常下單,因為下單后,訂單系統寫入消息隊列就不再關心其他的后續操作了。實現訂單系統與庫存系統的應用解耦。

 

流量削峰

流量削峰也是消息隊列中的常用場景,一般在秒殺或團搶活動中使用廣泛。

應用場景:秒殺活動,一般會因為流量過大,導致流量暴增,應用掛掉。為解決這個問題,一般需要在應用前端加入消息隊列:可以控制活動的人數;可以緩解短時間內高流量壓垮應用。

 

 

用戶的請求,服務器接收后,首先寫入消息隊列。假如消息隊列長度超過最大數量,則直接拋棄用戶請求或跳轉到錯誤頁面;秒殺業務根據消息隊列中的請求信息,再做后續處理。

 

日志處理

日志處理是指將消息隊列用在日志處理中,比如 Kafka 的應用,解決大量日志傳輸的問題。架構簡化如下:

 

日志采集客戶端,負責日志數據采集,定時寫入 Kafka隊列:Kafka 消息隊列,負責日志數據的接收,存儲和轉發;日志處理應用:訂閱並消費 kafka隊列中的日志數據;

 

消息通訊

消息通訊是指,消息隊列一般都內置了高效的通信機制,因此也可以用在純的消息通訊。比如實現點對點消息隊列,或者聊天室等。

點對點通訊:客戶端 A 和客戶端 B 使用同一隊列,進行消息通訊。

聊天室通訊:客戶端 A,客戶端 B,客戶端 N 訂閱同一主題,進行消息發布和接收。實現類似聊天室效果。

 

消息中間件的編年史

 

卡夫卡與法國作家馬塞爾·普魯斯特,愛爾蘭作家詹姆斯·喬伊斯並稱為西方現代主義文學的先驅和大師。《變形記》是卡夫卡的短篇代表作,是卡夫卡的藝術成就中的一座高峰,被認為是 20 世紀最偉大的小說作品之一。

 

常見的消息中間件比較

 

 

 

 

如果一般的業務系統要引入 MQ,怎么選型:

用戶訪問量在 ActiveMQ 的可承受范圍內,而且確實主要是基於解耦和異步來用的,可以考慮 ActiveMQ,也比較貼近 Java 工程師的使用習慣,但是ActiveMQ 現在停止維護了,同時 ActiveMQ 並發不高,所以業務量一定的情況下可以考慮使用。

RabbitMQ 作為一個純正血統的消息中間件,有着高級消息協議 AMQP 的完美結合,在消息中間件中地位無可取代,但是 erlang 語言阻止了我們去深入研究和掌控,對公司而言,底層技術無法控制,但是確實是開源的,有比較穩定的支持,活躍度也高。

對自己公司技術實力有絕對自信的,可以用 RocketMQ 

 

所以中小型公司,技術實力較為一般,技術挑戰不是特別高,用 ActiveMQ、RabbitMQ 是不錯的選擇;大型公司,基礎架構研發實力較強,用 RocketMQ是很好的選擇

如果是大數據領域的實時計算、日志采集等場景,用 Kafka 是業內標准的,絕對沒問題,社區活躍度很高,幾乎是全世界這個領域的事實性規范。

整體上來看,使用文件系統的消息中間件(kafka、rokcetMq)性能是最好的,所以基於文件系統存儲的消息中間件是發展趨勢。(從存儲方式和效率來看 文件系統>KV 存儲>關系型數據庫)


免責聲明!

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



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