MQ消息中间件选型
我們在做架構的時候經常面臨各種技術框架的選型,其中消息隊列基本上對于一些高并發的互聯網項目是必不可少的,那么話說回來我們在做消息隊列選型的時候是否問過如下幾個問題呢?
-
為什么使用消息隊列啊?
-
消息隊列有什么優點和缺點啊?
-
kafka、activemq、rabbitmq、rocketmq都有什么區別以及適合哪些場景?
如果你思考過如上幾個問題,那么恭喜你,你正在向一個合格的架構師邁進。很多時候不要因為使用而使用,你要清楚的知道為什么要使用,能解決什么樣的問題等。?
(1)我之前面試就見過有一部分候選人,說自己項目里用了redis、mq,但是一問其實他都并不知道自己為什么要用這個東西。其實說白了,就是為了用而用,或者是別人設計的架構,他從頭到尾沒思考過。沒有對自己的架構問過為什么的人,一定是平時沒有思考的人。(希望你不要成為這種人 haha)
(2)另外就是你要思考系統中引入消息隊列之后會不會有什么壞處?你要是沒考慮過這個,那你盲目弄個MQ進系統里,后面出了問題你能不能解決,解決花費的代價有多大?你要是沒考慮過引入一個技術可能存在的弊端和風險,那就是在給自己和同事挖坑了。
(3)然后就是既然用了MQ,那么具體是哪一種MQ,當時做沒做過調研呢??
?
千萬別傻乎乎的自己拍腦袋看個人喜好就瞎用了一個MQ,比如kafka。甚至都從沒調研過業界到底流行的MQ有哪幾種?每一個MQ的優點和缺點是什么?每一個MQ沒有絕對的好壞,但是就是看用在哪個場景可以揚長避短,利用其優勢,規避其劣勢。
那么接下來針對以上3個問題做一下簡單剖析
?(1)為什么使用消息隊列?
先說一下消息隊列的常見使用場景,其實場景有很多,但是比較核心的有3個:解耦、異步、削峰
解耦:
未采用MQ時系統間的調用案例:A系統發送個數據到BCD三個系統,接口調用發送,那如果E系統也要這個數據呢?那如果C系統現在不需要了呢?現在A系統又要發送第二種數據了呢?A系統負責人瀕臨崩潰中。。。再來點更加崩潰的事兒,A系統要時時刻刻考慮BCDE四個系統如果掛了咋辦?我要不要重發?我要不要把消息存起來?頭發都白了啊。。。
?
采用MQ解耦后的效果圖如下:系統A并不在關心誰需要使用它的數據,往MQ中一扔,誰要用自己去取就是了。即通過MQ后系統A與其它各系統之間徹底解耦了。
?
異步:
未采用MQ異步時的調用案例:A系統接收一個請求,需要在自己本地寫庫,還需要在BCD三個系統寫庫,自己本地寫庫要3ms,BCD三個系統分別寫庫要300ms、450ms、200ms。最終請求總延時是3 + 300 + 450 + 200 = 953ms,接近1s,用戶感覺搞個什么東西,慢死了慢死了。
?
采用MQ異步時的效果如下圖:系統A將請求發送給MQ,其它個系統通過后臺線程各自去執行即可,系統A不用管等待直接返回,給用戶的感覺將是瞬間響應,極大的提升了用戶體驗。
?
削峰:
未采用MQ削峰時的案例:每天0點到11點,A系統風平浪靜,每秒并發請求數量就100個。結果每次一到11點~1點,每秒并發請求數量突然會暴增到1萬條。但是系統最大的處理能力就只能是每秒鐘處理1000個請求啊。。。尷尬了,系統會死。。。
?
采用了MQ削峰時的效果圖如下:將高并發下的大量請求壓入MQ中,減少了服務器的壓力,防止數據庫服務器直接被大流量打死,從而造成整個系統宕機。
(2)消息隊列有什么優點和缺點啊?
優點上面已經說了,就是在特殊場景下有其對應的好處,解耦、異步、削峰?。
缺點呢?顯而易見的有如下幾個方面:
?
系統可用性降低:系統引入的外部依賴越多,越容易掛掉,本來你就是A系統調用BCD三個系統的接口就好了,人ABCD四個系統好好的,沒啥問題,你偏加個MQ進來,萬一MQ掛了咋整?MQ掛了,整套系統崩潰了,你不就完了么。?
?
系統復雜性提高:硬生生加個MQ進來,你怎么保證消息沒有重復消費?怎么處理消息丟失的情況?怎么保證消息傳遞的順序性?頭大頭大,問題一大堆,痛苦不已。?
?
一致性問題:A系統處理完了直接返回成功了,人都以為你這個請求就成功了;但是問題是,要是BCD三個系統那里,BD兩個系統寫庫成功了,結果C系統寫庫失敗了,咋整?你這數據就不一致了。?
?
tip:對于以上所說的缺點,系統可用性降低、系統復雜性提高、一致性問題將在后續文章中依次解答,持續關注公眾號“蝦米聊吧”
?
所以消息隊列實際是一種非常復雜的架構,你引入它有很多好處,但是也得針對它帶來的壞處做各種額外的技術方案和架構來規避掉,可能系統復雜度提升了一個數量級,也許是復雜了10倍。但是關鍵時刻,用,還是得用的。。。?
?
(3)kafka、activemq、rabbitmq、rocketmq都有什么優點和缺點啊?
常見的MQ其實就這幾種,別的還有很多其他MQ,但是比較冷門的,那么就別多說了
作為一個碼農,你起碼得知道各種mq的優點和缺點吧,咱們來畫個表格看看???
| 特性 | ActiveMQ | RabbitMQ | RocketMQ | Kafka |
| 單機吞吐量 | 萬級,吞吐量比RocketMQ和Kafka要低了一個數量級 | 萬級,吞吐量比RocketMQ和Kafka要低了一個數量級 | 10萬級,RocketMQ也是可以支撐高吞吐的一種MQ | 10萬級別,這是kafka最大的優點,就是吞吐量高。 ? 一般配合大數據類的系統來進行實時數據計算、日志采集等場景 |
| topic數量對吞吐量的影響 | ? | ? | topic可以達到幾百,幾千個的級別,吞吐量會有較小幅度的下降 ? 這是RocketMQ的一大優勢,在同等機器下,可以支撐大量的topic | topic從幾十個到幾百個的時候,吞吐量會大幅度下降 ? 所以在同等機器下,kafka盡量保證topic數量不要過多。如果要支撐大規模topic,需要增加更多的機器資源 |
| 時效性 | ms級 | 微秒級,這是rabbitmq的一大特點,延遲是最低的 | ms級 | 延遲在ms級以內 |
| 可用性 | 高,基于主從架構實現高可用性 | 高,基于主從架構實現高可用性 | 非常高,分布式架構 | 非常高,kafka是分布式的,一個數據多個副本,少數機器宕機,不會丟失數據,不會導致不可用 |
| 消息可靠性 | 有較低的概率丟失數據 | ? | 經過參數優化配置,可以做到0丟失 | 經過參數優化配置,消息可以做到0丟失 |
| 功能支持 | MQ領域的功能極其完備 | 基于erlang開發,所以并發能力很強,性能極其好,延時很低 | MQ功能較為完善,還是分布式的,擴展性好 | 功能較為簡單,主要支持簡單的MQ功能,在大數據領域的實時計算以及日志采集被大規模使用,是事實上的標準 |
| 優劣勢總結 | 非常成熟,功能強大,在業內大量的公司以及項目中都有應用 ? 偶爾會有較低概率丟失消息 ? 而且現在社區以及國內應用都越來越少,官方社區現在對ActiveMQ 5.x維護越來越少,幾個月才發布一個版本 ? 而且確實主要是基于解耦和異步來用的,較少在大規模吞吐的場景中使用 ? | erlang語言開發,性能極其好,延時很低; ? 吞吐量到萬級,MQ功能比較完備 ? 而且開源提供的管理界面非常棒,用起來很好用 ? 社區相對比較活躍,幾乎每個月都發布幾個版本分 ? 在國內一些互聯網公司近幾年用rabbitmq也比較多一些 ? 但是問題也是顯而易見的,RabbitMQ確實吞吐量會低一些,這是因為他做的實現機制比較重。 ? 而且erlang開發,國內有幾個公司有實力做erlang源碼級別的研究和定制?如果說你沒這個實力的話,確實偶爾會有一些問題,你很難去看懂源碼,你公司對這個東西的掌控很弱,基本職能依賴于開源社區的快速維護和修復bug。 ? 而且rabbitmq集群動態擴展會很麻煩,不過這個我覺得還好。其實主要是erlang語言本身帶來的問題。很難讀源碼,很難定制和掌控。 | 接口簡單易用,而且畢竟在阿里大規模應用過,有阿里品牌保障 ? 日處理消息上百億之多,可以做到大規模吞吐,性能也非常好,分布式擴展也很方便,社區維護還可以,可靠性和可用性都是ok的,還可以支撐大規模的topic數量,支持復雜MQ業務場景 ? 而且一個很大的優勢在于,阿里出品都是java系的,我們可以自己閱讀源碼,定制自己公司的MQ,可以掌控 ? 社區活躍度相對較為一般,不過也還可以,文檔相對來說簡單一些,然后接口這塊不是按照標準JMS規范走的有些系統要遷移需要修改大量代碼 ? ? | kafka的特點其實很明顯,就是僅僅提供較少的核心功能,但是提供超高的吞吐量,ms級的延遲,極高的可用性以及可靠性,而且分布式可以任意擴展 ? 同時kafka最好是支撐較少的topic數量即可,保證其超高吞吐量 ? 而且kafka唯一的一點劣勢是有可能消息重復消費,那么對數據準確性會造成極其輕微的影響,在大數據領域中以及日志采集中,這點輕微影響可以忽略 ? 這個特性天然適合大數據實時計算以及日志收集 |
??綜上所述,各種對比之后,我個人傾向于是:?
對于RabbitMQ,由于是erlang語言阻止了大量的java工程師去深入研究和掌控它,對公司而言,幾乎處于不可控的狀態,但是確實是開源的,比較穩定的支持,活躍度也高。
不過現在確實越來越多的公司,會去用RocketMQ,確實很不錯,對自己公司技術實力有絕對自信的,我推薦用RocketMQ,否則就用RabbitMQ吧,畢竟活躍開源社區,也不那么復雜。
所以中小型公司,技術實力較為一般,技術挑戰不是特別高,用RabbitMQ是不錯的選擇;大型公司,基礎架構研發實力較強,用RocketMQ是很好的選擇。?
如果是大數據領域的實時計算、日志采集等場景,用Kafka是業內標準的,絕對沒問題,社區活躍度很高,何況幾乎是全世界這個領域的事實性規范。
? 參考:石杉筆記
?
關注微信公眾號“蝦米聊吧”,后續持續放送“技術架構”干貨!!!
| ? ?一個熱衷于分享技術和生活的程序猿,讓我們一起交流吧~?????? ?? ? ? ? ? ? ? ?? ? ? ? ? ? ? ? ? ? ? ? ? ? ? 微信掃描二維碼,關注我的公眾號 |
?
總結
- 上一篇: 基于App SDK和API搭建无人自习室
- 下一篇: 云服务器10m宽带可以支持多少流量访问