1. 為什麼要用MQ
訊息佇列是一種“先進先出”的資料結構
其應用場景主要包含以下3個方面
- 應用解耦
系統的耦合性越高,容錯性就越低。以電商應用為例,使用者建立訂單後,如果耦合呼叫庫存系統、物流系統、支付系統,任何一個子系統出了故障或者因為升級等原因暫時不可用,都會造成下單操作異常,影響使用者使用體驗。
使用訊息佇列解耦合,系統的耦合性就會提高了。比如物流系統發生故障,需要幾分鐘才能來修復,在這段時間內,物流系統要處理的資料被快取到訊息佇列中,使用者的下單操作正常完成。當物流系統回覆後,補充處理存在訊息佇列中的訂單訊息即可,終端系統感知不到物流系統發生過幾分鐘故障。
- 流量削峰
應用系統如果遇到系統請求流量的瞬間猛增,有可能會將系統壓垮。有了訊息佇列可以將大量請求快取起來,分散到很長一段時間處理,這樣可以大大提到系統的穩定性和使用者體驗。
一般情況,為了保證系統的穩定性,如果系統負載超過閾值,就會阻止使用者請求,這會影響使用者體驗,而如果使用訊息佇列將請求快取起來,等待系統處理完畢後通知使用者下單完畢,這樣總不能下單體驗要好。
處於經濟考量目的:
業務系統正常時段的QPS如果是1000,流量最高峰是10000,為了應對流量高峰配置高效能的伺服器顯然不划算,這時可以使用訊息佇列對峰值流量削峰
- 資料分發
通過訊息佇列可以讓資料在多個系統更加之間進行流通。資料的產生方不需要關心誰來使用資料,只需要將資料傳送到訊息佇列,資料使用方直接在訊息佇列中直接獲取資料即可
2. MQ
的優點和缺點
優點:解耦、削峰、資料分發
缺點包含以下幾點:
-
系統可用性降低
系統引入的外部依賴越多,系統穩定性越差。一旦MQ當機,就會對業務造成影響。
如何保證MQ的高可用?
-
系統複雜度提高
MQ的加入大大增加了系統的複雜度,以前系統間是同步的遠端呼叫,現在是通過MQ進行非同步呼叫。
如何保證訊息沒有被重複消費?怎麼處理訊息丟失情況?那麼保證訊息傳遞的順序性?
-
一致性問題
A系統處理完業務,通過
MQ
給B、C、D三個系統發訊息資料,如果B系統、C系統處理成功,D系統處理失敗。如何保證訊息資料處理的一致性?
3. 各種MQ
產品的比較
常見的MQ產品包括Kafka
、ActiveMQ
、RabbitMQ
、RocketMQ
。
4. 安裝RocketMQ
RocketMQ
是阿里巴巴2016年MQ
中介軟體,使用Java
語言開發,在阿里內部,RocketMQ
承接了例如“雙11”等高併發場景的訊息流轉,能夠處理萬億級別的訊息。
4.1 下載RocketMQ
RocketMQ最新版本:4.5.1
4.2 環境要求
-
Linux64位系統
-
JDK1.8(64位)
yum install java-1.8.0-openjdk* -y
- 原始碼安裝需要安裝Maven 3.2.x
4.3 二進位制包方式安裝RocketMQ
本教程以二進位制包方式安裝
- 解壓安裝包
- 進入安裝目錄
目錄介紹
bin
:啟動指令碼,包括shell
指令碼和CMD
指令碼conf
:例項配置檔案 ,包括broker
配置檔案、logback
配置檔案等lib
:依賴jar
包,包括Netty
、commons-lang
、FastJSON
等
4.4 啟動RocketMQ
- 啟動
NameServer
# 1.啟動NameServer
nohup sh bin/mqnamesrv &
# 2.檢視啟動日誌
tail -f ~/logs/rocketmqlogs/namesrv.log
- 啟動
Broker
# 1.啟動Broker
nohup sh bin/mqbroker -n localhost:9876 &
# 2.檢視啟動日誌
tail -f ~/logs/rocketmqlogs/broker.log
-
問題描述:
RocketMQ
預設的虛擬機器記憶體較大,啟動Broker
如果因為記憶體不足失敗,需要編輯如下兩個配置檔案,修改JVM
記憶體大小
# 編輯runbroker.sh和runserver.sh修改預設JVM大小
vi runbroker.sh
vi runserver.sh
- 參考設定:
JAVA_OPT="${JAVA_OPT} -server -Xms256m -Xmx256m -Xmn128m -XX:MetaspaceSize=128m -XX:MaxMetaspaceSize=320m"
5 測試RocketMQ
5.1 傳送訊息
# 1.設定環境變數
export NAMESRV_ADDR=localhost:9876
# 2.使用安裝包的Demo傳送訊息
sh bin/tools.sh org.apache.rocketmq.example.quickstart.Producer
5.2 接收訊息
# 1.設定環境變數
export NAMESRV_ADDR=localhost:9876
# 2.接收訊息
sh bin/tools.sh org.apache.rocketmq.example.quickstart.Consumer
6. 關閉RocketMQ
# 1.關閉NameServer
sh bin/mqshutdown namesrv
# 2.關閉Broker
sh bin/mqshutdown broker