消息隊列之概論
什麼是消息隊列?消息隊列能做什麼?消息隊列為什麼會出現?再說消息隊列之前我們要先知道什麼是消息隊列、能夠做什麼、為什麼會出現消息隊列?
1、什麼是消息隊列
消息隊列是在分布式系統中最常用的且最重要的元件之一,這個分布式系統不是指你的一個服務部署到不同的機器中,如果你是一個相同的服務部署到不同的機器這種不能稱之為分布式系統,準确來說應該說是叢集服務,而分布式系統通常是指有很多個不同的服務分别部署到不同的伺服器中,
如圖:
,如何在不同的服務中進行快速的資料互動或者調用,通常有兩種方式分别是RPC調用和消息隊列,常見的RPC調用分别有Http、GRPC等。而消息隊列的方式是指由三個重要部分分别是《消息生産者、消息服務中心、消息消費者》組成。![]()
消息隊列之概論
- 生産者: 消息的生産者隻負責将消息發送給消息服務中心,它隻在意消息是否成功的存儲在了消息隊列服務中。
- 消息服務中心: 消息服務中心其實可以當做一個中間商來看,其實它的作用就是将資料持久化到自己服務内,不在意是誰發送的消息。
- 消息消費者: 消息消費者是指從中間商擷取消息的一個部分,它隻在意我是否能拿到消息至于是誰釋出的它不在意。
2、消息隊列能做什麼
消息隊列可以做:應用解耦、流量削峰、日志收集、消息通訊、事務最終一緻性等場景都可以使用消息隊列。
2.1、流量削峰
什麼是流量削峰,在網際網路行業中,可能會在某一個時間段網站迎來使用者的請求高峰期的> 情況例如(12306、淘寶雙十一)等,在系統設計之初可能隻是簡單寫入資料庫,但是如果一直延續這樣的設計遇到高峰期的請求就會給資料庫帶來巨大的壓力,并發量超出了系統的承載能力可能會引起系統雪崩。當通路量劇增的> 時候系統一覽可以繼續使用最常見的是使用消息隊列,将短時間的高并發請求持久化到消息隊列服務中,進而實作削平高峰期的請求并發流量,改善系統性能。
2.2、系統解耦
在大型系統的開發過程中會經常碰到 類情況 随着需求的疊加 各子產品之間逐漸變成了互相調用的關系,這種子產品間緊密關聯的關系就是緊相合 緊相合帶來的問題是對一個子產品的功能變更将導緻其關聯子產品發生變化,是以各個子產品難以獨立演要解決這個題,可以在子產品之間調用時增加 個中問層來實作解楠,這也友善了以後的 擴充。所謂解锢,簡單地講,就是一個子產品隻關心自己的核心流程,而依賴該棋塊執行結果的其他子產品如果做的不是很重要的事情,有通知即可,無須等待結果 換句話說,基于消息隊列的模型,關心的是通 ,而非處理。
2.3、事務最終一緻性
如果系統很小,将兩個表存儲在相同的資料庫中,我們可以通過資料庫的強一緻性事務進行管理,如果我們是大型系統需要操作不同的資料庫完成一個業務那麼就無法使用資料庫事務來完成了,?業界曾經提出過 個處理分布式事務的規範 XAo XA 主要定義了全事務管理器( Transaction Manager )和局部資料總管( Resource Manager )之間的接。 XA接口是雙向的系統接口,在事務管理器及 個或多個資料總管之間形成通信橋梁。兀氣引入事務管理器充當全局事務中的協調者的角色。事務管理器控制着全局事務,管理事務生命周期,并協調資源。資料總管負責控制和管理實際資源(如資料庫或 JMS 隊列)。目前各主流資料庫都提供了對凡氣規範的支援。它的缺陷是性能很差,不适合高并發和高性能要求的場景。我們可以通過消息隊列來處理事務問題,其實在分布式事務中最主要的是CAP定理,和Base理論,在此不詳細介紹CAP定理和Base理論,具體的可以自行百度。
2.4、日志收集
消息隊列也可以用來做日志收集,在項目運作中日志也是一個很重要的組成部分,可以通過日志跟蹤調試資訊、定位問題、使用者操作行為等等。具體的日志分析就需要大資料來進行分析了,日志收集的消息隊列用的最多的就是kafka。
3、消息服務中心的功能與特點
消息隊列它包含了兩個關鍵詞《消息和隊列》,消息是指在不通服務之間傳遞的具體資料,消息可以是各式各樣的;對于隊列的含義我個人了解的其實就是資料結構中隊列的概念,是指先進先出,消息的入隊和出隊并不一定是同步進行的,是以需要一個容器來暫存和處理消息,而消息服務中心就是這個容器。在上面有提到過三個重要的組成部分,分别是:消息生産者->Producer、消息服務中心->Broker、消息消費者->Consumer,除了這些一個好的消息隊列還應該具備以下功能:消息堆積、消息持久化、可靠投遞、消息重複、高可用叢集部署等各種問題。
3.1、消息堆積
因為消息隊列的生産者、消費者是兩個分開處理消息的系統,也無法預制兩者對消息的處理速度快慢,一旦在某個時間段内消費者的處理速度沒有跟上生産者發送消息的速度會導緻消息進行中心積壓無法及時得到釋放。是以一個好的消息隊列産品需要具備處理這種情況,比如通過設定一個閥值,超過閥值的消息不在放入進行中心等,避免消息中心系統資源耗盡,導緻消息中心服務當機。
3.2、消息持久化
在設計一個消息隊列時,如果生産者的消息到達消息服務中心不做任何處理就直接轉給消費者那麼消息服務中心的存在也就失去了意義,無法滿足流量削峰等需求,是以消息服務中心的正常做法都是将消息暫存到消息服務中心本地,然後擇機将消息投遞給消費者,消息的暫存可以在記憶體中,也可以選擇存儲到磁盤、資料庫、檔案等地方。将消息存放到記憶體中最大的問題就是一旦當機消息會丢失。如果你的業務場景要求消息不能丢失,那麼勢必需要将消息持久化,前面也有提到過持久化方案分為很多種。
3.3、可靠投遞
可靠投遞是指不允許存在消息途中丢失的情況。從消息的整個生命周期來分析的話,消息丢失的情況一般出現在以下過程中:
- 從生産者到消息服務中心
- 從消息服務中心到消息消費者
- 消息中心一旦當機是否持久化了消息
由于跨越不同系統,中間調用會朋友許多問題,例如網絡問題、系統當機等不确定的情形,但是對消息發送者來說都是一件事,消息沒有送達,在有些場景下需要保證消息不能丢失,例如網購時訂單支付成功消息不能丢失,否則這筆訂單會卡在未支付環節。
3.4、叢集
在大型系統應用中,系統架構一般都需要實作高可用性,用來排除單點故障引起的系統中斷,保證7*24小時不間斷運作,是以消息服務中心需要對叢集模式提供支援,叢集不僅可以讓消費者和生産者在某個節點當機的情況下繼續運作,叢集之間的多個節點還能夠共享負載,當某台機器或者網絡出現故障時自動進行負載均衡,進而保證多節點來提高消息通信的吞吐量。
4、主流消息服務中間件對比
特性 | ActiveMQ | RabbitMQ | RocketMQ | Kafka |
---|---|---|---|---|
單機吞吐量 | 萬級,與RocketMQ、kafka相比吞吐量略低 | 1W量級,與RocketMQ、kafka相比吞吐量略低 | 10 萬級,支撐高吞吐 | 10 萬級,高吞吐,一般配合大資料類的系統來進行實時資料計算、日志采集等場景 |
Topic數量對吞吐量的影響 | 未知 | topic 可以達到幾百/幾千的級别,吞吐量會有較小幅度的下降,這是 RocketMQ 的一大優勢,在同等機器下,可以支撐大量的 topic | topic 從幾十到幾百個時候,吞吐量會大幅度下降,在同等機器下,Kafka 盡量保證 topic 數量不要過多,如果要支撐大規模的 topic,需要增加更多的機器資源 | |
時效性 | ms 級 | 微秒級,這是 RabbitMQ 的一大特點,延遲最低 | 毫秒級 | 毫秒 |
可用性 | 可以基于主從架構實作高可用 | 很高(主從模式) | 非常高,分布式,一個資料多個副本,少數機器當機,不會丢失資料,不會導緻不可用 | |
消息丢失 | 有較低的機率丢失資料 | 基本不丢 | 參數優化配置,可以做到 0 丢失 | |
消費模式 | 推拉 | 拉取 | ||
優點 | MQ領域的功能極其完備 | 由于erlang語言的特性,mq 性能較好,高并發;健壯、穩定、易用、跨平台、支援多種語言、文檔齊全;社群活躍度高;路由機制完備 | MQ功能較為完善,還是分布式的,擴充性好,支援10億級别的消息堆積,不會因為堆積導緻性能下降 | 性能卓越,單機寫入TPS約在百萬條/秒,最大的優點,就是吞吐量高。 |
缺點 | 官方社群現在對ActiveMQ 5.x維護越來越少,較少在大規模吞吐的場景中使用。 | erlang開發,很難去看懂源碼,基本職能依賴于開源社群的快速維護和修複bug,不利于做二次開發和維護。RabbitMQ吞吐量會低一些,這是因為他做的實作機制比較重。需要學習比較複雜的接口和協定,學習和維護成本較高。 | 支援的用戶端語言不多,目前是java及c++,其中c++不成熟; 社群活躍度一般, 沒有在 mq 核心中去實作JMS等接口,有些系統要遷移需要修改大量代碼 | Kafka單機超過64個隊列/分區,Load會發生明顯的飙高現象,隊列越多,load越高,發送消息響應時間變長 |
總結
消息中間件是非底層作業系統軟體、非業務應用軟體,更不是直接面對最終使用者使用的,不能直接給使用者帶來價值的軟體統稱為中間件。消息中間件關注的是資料的發送和結構,利用高效、可靠的異步消息投遞機制內建成分布式系統。
學不完的技術,寫不完的代碼。QQ群:773595012
▼-----------------------------------------▼-----------------------------------------▼