我與訊息佇列的八年情緣

勇哥技術遊記發表於2022-01-12

談起訊息佇列,內心還是會有些波瀾。

訊息佇列,快取,分庫分表是高併發解決方案三劍客,而訊息佇列是我最喜歡,也是思考最多的技術。

我想按照下面的四個階段分享我與訊息佇列的故事,同時也是對我技術成長經歷的回顧。

  • 初識:ActiveMQ
  • 進階:Redis&RabbitMQ
  • 昇華:MetaQ
  • 鍾情:RocketMQ

1 初識ActiveMQ

1.1 非同步&解耦

2011年初,我在一家網際網路彩票公司做研發。

我負責的是使用者中心繫統,提供使用者註冊,查詢,修改等基礎功能。使用者註冊成功之後,需要給使用者傳送簡訊。

因為原來都是程式導向程式設計,我就把新增使用者模組和傳送簡訊模組都揉在一起了。

起初都還好,但問題慢慢的顯現出來。

  • 簡訊渠道不夠穩定,傳送簡訊會達到5秒左右,這樣使用者註冊介面耗時很大,影響前端使用者體驗;
  • 簡訊渠道介面發生變化,使用者中心程式碼就必須修改了。但使用者中心是核心系統。每次上線都必要謹小慎微。這種感覺很彆扭,非核心功能影響到核心系統了。

第一個問題,我可以採取執行緒池的方法來做,主要是非同步化。但第二個問題卻讓我束手無措。

於是我向技術經理請教,他告訴我引入訊息佇列去解決這個問題。

  • 將傳送簡訊功能單獨拆成獨立的Job服務;
  • 使用者中心使用者註冊成功後,傳送一條訊息到訊息佇列,Job服務收到訊息呼叫簡訊服務傳送簡訊即可。

這時,我才明白: 訊息佇列最核心的功能就是非同步解耦

1.2 排程中心

彩票系統的業務是比較複雜的。在彩票訂單的生命週期裡,經過建立,拆分子訂單,出票,算獎等諸多環節。
每一個環節都需要不同的服務處理,每個系統都有自己獨立的表,業務功能也相對獨立。假如每個應用都去修改訂單主表的資訊,那就會相當混亂了。

公司的架構師設計了排程中心的服務,排程中心的職責是維護訂單核心狀態機,訂單返獎流程,彩票核心資料生成。

排程中心通過訊息佇列和出票閘道器,算獎服務等系統傳遞和交換資訊。

這種設計在那個時候青澀的我的眼裡,簡直就是水滴vs人類艦隊,降維打擊。

隨著我對業務理解的不斷深入,我隱約覺得:“好的架構是簡潔的,也是應該易於維護的”。

當彩票業務日均千萬交易額的時候,排程中心的研發維護人員也只有兩個人。排程中心的原始碼裡業務邏輯,日誌,程式碼規範都是極好的。

在我日後的程式人生裡,我也會下意識模仿排程中心的編碼方式,“不玩奇技淫巧,程式碼是給人閱讀的”。

1.3 重啟大法

隨著彩票業務的爆炸增長,每天的訊息量從30萬激增到150~200萬左右,一切看起來似乎很平穩。

某一天雙色球投注截止,排程中心無法從訊息佇列中消費資料。訊息匯流排處於只能發,不能收的狀態下。 整個技術團隊都處於極度的焦慮狀態,“要是出不了票,那可是幾百萬的損失呀,要是使用者中了兩個雙色球?那可是千萬呀”。大家急得像熱鍋上的螞蟻。

這也是整個技術團隊第一次遇到消費堆積的情況,大家都沒有經驗。

首先想到的是多部署幾臺排程中心服務,部署完成之後,排程中心消費了幾千條訊息後還是Hang住了。 這時,架構師只能採用重啟的策略。你沒有看錯,就是重啟大法。說起來真的很慚愧,但當時真的只能採用這種方式。

排程中心重啟後,消費了一兩萬後又Hang住了。只能又重啟一次。來來回回持續20多次,像擠牙膏一樣。而且隨著出票截止時間的臨近,這種思想上的緊張和恐懼感更加強烈。終於,通過1小時的手工不斷重啟,訊息終於消費完了。

我當時正好在讀畢玄老師的《分散式java應用基礎與實踐》,猜想是不是執行緒阻塞了,於是我用Jstack命令檢視堆疊情況。 果然不出所料,執行緒都阻塞在提交資料的方法上。

我們馬上和DBA溝通,發現oracle資料庫執行了非常多的大事務,每次大的事務執行都需要30分鐘以上,導致排程中心的排程出票執行緒阻塞了。

技術部後來採取瞭如下的方案規避堆積問題:

  1. 生產者傳送訊息的時候,將超大的訊息拆分成多批次的訊息,減少排程中心執行大事務的機率;
  2. 資料來源配置引數,假如事務執行超過一定時長,自動拋異常,回滾。

1.4 覆盤

Spring封裝的ActiveMQ的API非常簡潔易用,使用過程中真的非常舒服。

受限於當時彩票技術團隊的技術水平和視野,我們在使用ActiveMQ中遇到了一些問題。

  1. 高吞吐下,堆積到一定訊息量易Hang住;

技術團隊發現在吞吐量特別高的場景下,假如訊息堆積越大,ActiveMQ有較小几率會Hang住的。

出票閘道器的訊息量特別大,有的訊息並不需要馬上消費,但是為了規避訊息佇列Hang住的問題,出票閘道器消費資料的時候,先將訊息先持久化到本地磁碟,生成本地XML檔案,然後非同步定時執行訊息。通過這種方式,我們大幅度提升了出票閘道器的消費速度,基本杜絕了出票閘道器佇列的堆積。

但這種方式感覺也挺怪的,消費訊息的時候,還要本地再儲存一份資料,訊息儲存在本地,假如磁碟壞了,也有丟訊息的風險。

  1. 高可用機制待完善

我們採用的master/slave部署模式,一主一從,伺服器配置是4核8G 。

這種部署方式可以同時執行兩個ActiveMQ, 只允許一個slave連線到Master上面,也就是說只能有2臺MQ做叢集,這兩個服務之間有一個資料備份通道,利用這個通道Master向Slave單向地資料備份。 這個方案在實際生產線上不方便, 因為當Master掛了之後, Slave並不能自動地接收Client發來的請來,需要手動干預,且要停止Slave再重啟Master才能恢復負載叢集。

還有一些很詭異丟訊息的事件,生產者傳送訊息成功,但master控制檯查詢不到,但slave控制檯竟然能查詢到該訊息。

但消費者沒有辦法消費slave上的訊息,還得通過人工介入的方式去處理。

2 進階Redis&RabbitMQ

2014年,我在藝龍網從事紅包系統和優惠券系統優化相關工作。

2.1 Redis可以做訊息佇列嗎

酒店優惠券計算服務使用的是初代流式計算框架Storm。Storm這裡就不詳細介紹,可以參看下面的邏輯圖:
storm說明

這裡我們的Storm叢集的水源頭(資料來源)是redis叢集,使用list資料結構實現了訊息佇列的push/pop功能。

流式計算的整體流程:

  1. 酒店資訊服務傳送酒店資訊到Redis叢集A/B;
  2. Storm的spout元件從Redis叢集A/B獲取資料, 獲取成功後,傳送tuple訊息給Bolt元件;
  3. Bolt元件收到訊息後,通過運營配置的規則對資料進行清洗;
  4. 最後Storm把處理好的資料傳送到Redis叢集C;
  5. 入庫服務從Redis叢集C獲取資料,儲存資料到資料庫;
  6. 搜尋團隊掃描資料庫表,生成索引。

storm說明

這套流式計算服務每天處理千萬條資料,處理得還算順利。
但方案在團隊內部還是有不同聲音:

  • storm的拓撲升級時候,或者優惠券服務重啟的時候,偶爾出現丟訊息的情況。但訊息的丟失,對業務來講沒有那麼敏感,而且我們也提供了手工重新整理的功能,也在業務的容忍範圍內;
  • 團隊需要經常關注Redis的快取使用量,擔心Redis佇列堆積, 導致out of memory;
  • 架構師認為搜尋團隊直接掃描資料庫不夠解耦,建議將Redis叢集C替換成Kafka,搜尋團隊從kafka直接消費訊息,生成索引;

我認為使用Redis做訊息佇列應該滿足如下條件:

  1. 容忍小概率訊息丟失,通過定時任務/手工觸發達到最終一致的業務場景;
  2. 訊息堆積概率低,有相關的報警監控;
  3. 消費者的消費模型要足夠簡單。

2.2 RabbitMQ是管子不是池子

RabbitMQ是用erlang語言編寫的。RabbitMQ滿足了我的兩點需求:

  1. 高可用機制。藝龍內部是使用的映象高可用模式,而且這種模式在藝龍已經使用了較長時間了,穩定性也得到了一定的驗證。
  2. 我負責的紅包系統裡,RabbitMQ每天的吞吐也在百萬條訊息左右,訊息的傳送和消費都還挺完美。

優惠券服務原使用SqlServer,由於資料量太大,技術團隊決定使用分庫分表的策略,使用公司自主研發的分散式資料庫DDA。

因為是第一次使用分散式資料庫,為了測試DDA的穩定性,我們模擬傳送1000萬條訊息到RabbitMQ,然後優惠券重構服務消費訊息後,按照使用者編號hash到不同的mysql庫。

RabbitMQ叢集模式是映象高可用,3臺伺服器,每臺配置是4核8G 。

我們以每小時300萬條訊息的速度傳送訊息,最開始1個小時生產者和消費者表現都很好,但由於消費者的速度跟不上生產者的速度,導致訊息佇列有積壓情況產生。第三個小時,訊息佇列已堆積了500多萬條訊息了, 生產者傳送訊息的速度由最開始的2毫秒激增到500毫秒左右。RabbitMQ的控制檯已血濺當場,標紅報警。

這是一次無意中的測試,從測試的情況來看,RabbitMQ很優秀,但RabbitMQ對訊息堆積的支援並不好,當大量訊息積壓的時候,會導致 RabbitMQ 的效能急劇下降

有的朋友對我講:“RabbitMQ明明是管子,你非得把他當池子?”

隨著整個網際網路資料量的激增, 很多業務場景下是允許適當堆積的,只要保證消費者可以平穩消費,整個業務沒有大的波動即可。

我心裡面越來越相信:訊息佇列既可以做管子,也可以當做池子

3 昇華MetaQ

Metamorphosis的起源是我從對linkedin的開源MQ–現在轉移到apache的kafka的學習開始的,這是一個設計很獨特的MQ系統,它採用pull機制,而 不是一般MQ的push模型,它大量利用了zookeeper做服務發現和offset儲存,它的設計理念我非常欣賞並贊同,強烈建議你閱讀一下它的設計文件,總體上說metamorphosis的設計跟它是完全一致的。--- MetaQ的作者莊曉丹

3.1 驚豔消費者模型

2015年,我主要從事神州專車訂單研發工作。

MetaQ滿足了我對於訊息佇列的幻想:“分散式,高吞吐,高堆積”。

MetaQ支援兩種消費模型: 叢集消費廣播消費 ,因為以前使用過的消費者模型都是用佇列模型,當我第一次接觸到這種釋出訂閱模型的時候還是被驚豔到了。

▍ 叢集消費

訂單建立成功後,傳送一條訊息給MetaQ。這條訊息可以被派單服務消費,也可以被BI服務消費。

▍ 廣播消費

派單服務在講訂單指派給司機的時候,會給司機傳送一個推送訊息。推送就是用廣播消費的模式實現的。

大體流程是:

  1. 司機端推送服務是一個TCP服務,啟動後,採用的是廣播模式消費MetaQ的PushTopic;
  2. 司機端會定時傳送TCP請求到推送服務,鑑權成功後,推送服務會儲存司機編號和channel的引用;
  3. 派單服務傳送推送訊息到MetaQ;
  4. 推送服務的每一臺機器都會收到該訊息,然後判斷記憶體中是否存在該司機的channel引用,若存在,則推送訊息。

這是非常經典的廣播消費的案例。我曾經研讀京麥TCP閘道器的設計,它的推送也是採用類似的方式。

3.2 激進的消峰

2015年是叫車大戰硝煙瀰漫的一年。

對神州專車來講,隨著訂單量的不斷增長,欣喜的同時,效能的壓力與日俱增。早晚高峰期,使用者叫車的時候,經常點選下單經常無響應。
在系統層面來看,專車api閘道器發現大規模超時,訂單服務的效能急劇下降。資料庫層面壓力更大,高峰期一條記錄插入竟然需要8秒的時間。

整個技術團隊需要儘快提升專車系統的效能,此前已經按照模組領域做了資料庫的拆分。但系統的瓶頸依然很明顯。

我們設計了現在看來有點激進的方案:

  1. 設計訂單快取。快取方案大家要有興趣,我們可以以後再聊,裡面有很多可以詳聊的點;
  2. 在訂單的載客生命週期裡,訂單的修改操作先修改快取,然後傳送訊息到MetaQ,訂單落盤服務消費訊息,並判斷訂單資訊是否正常(比如有無亂序),若訂單資料無誤,則儲存到資料庫中。

這裡有兩個細節:

  1. 消費者消費的時候需要順序消費,實現的方式是按照訂單號路由到不同的partition,同一個訂單號的訊息,每次都發到同一個partition;

  2. 一個守護任務,定時輪詢當前正在進行的訂單,當快取與資料不一致時候,修復資料,併傳送報警。

這次優化大大提升訂單服務的整體效能,也為後來訂單服務庫分庫分表以及異構打下了堅實的基礎,根據我們的統計資料,基本沒有發生過快取和資料庫最後不一致的場景。 但這種方案對快取高可用有較高的要求,還是有點小激進吧。

3.3 訊息SDK封裝

做過基礎架構的同學可能都有經驗:“三方元件會封裝一層”,神州架構團隊也是將metaq-client封裝了一層。

在我的思維裡面,封裝一層可以減少研發人員使用第三方元件的心智投入,統一技術棧,也就如此了。

直到發生一次意外,我的思維升級了。那是一天下午,整個專車服務崩潰較長時間。技術團隊發現:"專車使用zookeeper做服務發現。zk叢集的leader機器掛掉了,一直在選主。"

臨時解決後,我們發現MetaQ和服務發現都使用同一套zk叢集,而且consumer的offset提交,以及負載均衡都會對zk叢集進行大量的寫操作。

為了減少MetaQ對zk叢集的影響,我們的目標是:“MetaQ使用獨立的zk叢集”。

  1. 需要部署新的zk叢集;
  2. MetaQ的zk資料需要同步到新的叢集;
  3. 保證切換到新的叢集,應用服務基本無感知。

我很好奇向架構部同學請教,他說新的叢集已經部署好了,但需要同步zk資料到新的叢集。他在客戶端裡新增了雙寫的操作。也就是說:我們除了會寫原有的zk叢集一份資料,同時也會在新的zk叢集寫一份。
過了幾周後,MetaQ使用獨立的zk叢集這個任務已經完成了。

這一次的經歷帶給我很大的感慨:“還可以這麼玩?” ,也讓我思考著:三方元件封裝沒有想像中那麼簡單。

我們可以看下快手訊息的SDK封裝策略:

  1. 對外只提供最基本的 API,所有訪問必須經過SDK提供的介面。簡潔的 API 就像冰山的一個角,除了對外的簡單介面,下面所有的東西都可以升級更換,而不會破壞相容性 ;
  2. 業務開發起來也很簡單,只要需要提供 Topic(全域性唯一)和 Group 就可以生產和消費,不用提供環境、NameServer 地址等。SDK 內部會根據 Topic 解析出叢集 NameServer 的地址,然後連線相應的叢集。生產環境和測試環境環境會解析出不同的地址,從而實現了隔離;
  3. 上圖分為 3 層,第二層是通用的,第三層才對應具體的 MQ 實現,因此,理論上可以更換為其它訊息中介軟體,而客戶端程式不需要修改;
  4. SDK 內部整合了熱變更機制,可以在不重啟 Client 的情況下做動態配置,比如下發路由策略(更換叢集 NameServer 的地址,或者連線到別的叢集去),Client 的執行緒數、超時時間等。通過 Maven 強制更新機制,可以保證業務使用的 SDK 基本上是最新的。

3.4 重構MetaQ , 自成體系

我有一個習慣 : "經常找運維,DBA,架構師瞭解當前系統是否有什麼問題,以及他們解決問題的思路。這樣,我就有另外一個視角來審視公司的系統執行情況"。

MetaQ也有他的缺點。

  1. MetaQ的基層通訊框架是gecko,MetaQ偶爾會出現rpc無響應,應用假死的情況,不太好定位問題;
  2. MetaQ的運維能力薄弱,只有簡單的Dashboard介面,無法實現自動化主題申請,訊息追蹤等功能。

有一天,我發現測試環境的一臺消費者伺服器啟動後,不斷報連結異常的問題,而且cpu佔用很高。我用netstat命令馬上查一下,發現已經建立了幾百個連結。出於好奇心,我開啟了原始碼,發現網路通訊框架gecko已經被替換成了netty。我們馬上和架構部的同學聯絡。

我這才明白:他們已經開始重構MetaQ了。我從來沒有想過重構一個開源軟體,因為距離我太遠了。或者那個時候,我覺得自己的能力還達不到。

後來,神州自研的訊息佇列自成體系了,已經在生產環境執行的挺好。

時至今天,我還是很欣賞神州架構團隊。他們自研了訊息佇列,DataLink(資料異構中介軟體),分庫分表中介軟體等。他們願意去創新,有勇氣去做一個更好的技術產品。

我從他們身上學到很多。

也許在看到他們重構MetaQ的那一刻,我的心裡埋下了種子。

4 鍾情RocketMQ

4.1 開源的盛宴

2014年,我搜羅了很多的淘寶的訊息佇列的資料,我知道MetaQ的版本已經升級MetaQ 3.0,只是開源版本還沒有放出來。

大約秋天的樣子,我加入了RocketMQ技術群。誓嘉(RocketMQ創始人)在群裡說:“最近要開源了,放出來後,大家趕緊fork呀”。他的這句話發在群裡之後,群裡都炸開了鍋。我更是歡喜雀躍,期待著能早日見到阿里自己內部的訊息中介軟體。

終於,RocketMQ終於開源了。我迫不及待想一窺他的風采。

因為我想學網路程式設計,而RocketMQ的通訊模組remoting底層也是Netty寫的。所以,RocketMQ的通訊層是我學習切入的點。

我模仿RocketMQ的remoting寫了一個玩具的rpc,這更大大提高我的自信心。正好,藝龍舉辦技術創新活動。我想想,要不嘗試一下用Netty改寫下Cobar的通訊模組。於是參考Cobar的原始碼花了兩週寫了個netty版的proxy,其實非常粗糙,很多功能不完善。後來,這次活動頒給我一個鼓勵獎,現在想想都很好玩。

因為在神州優車使用MetaQ的關係,我學習RocketMQ也比較得心應手。為了真正去理解原始碼,我時常會參考RocketMQ的原始碼,寫一些輪子來驗證我的學習效果。

雖然自己做了一些練習,但一直沒有在業務環境使用過。2018年是我真正使用RocketMQ的一年,也是有所得的一年。

▍ 簡訊服務

簡訊服務應用很廣泛,比如使用者註冊登入驗證碼,營銷簡訊,下單成功簡訊通知等等。
最開始設計簡訊服務的時候,我想學習業界是怎麼做的。於是把目標鎖定在騰訊雲的簡訊服務上。
騰訊雲的簡訊服務有如下特點:

  • 統一的SDK,後端入口是http/https服務 , 分配appId/appSecret鑑權;
  • 簡潔的API設計:單發,群發,營銷單發,營銷群發,模板單發,模板群發。

於是,我參考了這種設計思路。

  1. 模仿騰訊雲的SDK設計,提供簡單易用的簡訊介面;
  2. 設計簡訊服務API端,接收發簡訊請求,傳送簡訊資訊到訊息佇列;
  3. worker服務消費訊息,按照負載均衡的演算法,呼叫不同渠道商的簡訊介面;
  4. Dashboard可以檢視簡訊傳送記錄,配置渠道商資訊。

簡訊服務是我真正意義第一次生產環境使用RocketMQ,當簡訊一條條發出來的時候,還是蠻有成就感的。

▍ MQ控制檯

使用過RocketMQ的朋友,肯定對上圖的控制檯很熟悉。當時團隊有多個RocketMQ叢集,每組叢集都需要單獨部署一套控制檯。於是我想著:能不能稍微把控制檯改造一番,能滿足支援多組叢集。

於是,擼起袖子幹了起來。大概花了20天的時間,我們基於開源的版本改造了能支援多組叢集的版本。做完之後,雖然能滿足我最初的想法,但是做的很粗糙。而且搜狐開源了他們自己的MQCloud ,我看了他們的設計之後, 覺得離一個訊息治理平臺還很遠。

後來我讀了《網易雲音樂的訊息佇列改造之路》,《今日頭條在訊息服務平臺和容災體系建設方面的實踐與思考》這兩篇文章,越是心癢難耐,蠻想去做的是一個真正意義上的訊息治理平臺。一直沒有什麼場景和機會,還是有點可惜。

最近看了哈羅單車架構專家樑勇的一篇文章《哈囉在分散式訊息治理和微服務治理中的實踐》,推薦大家一讀。

https://mp.weixin.qq.com/s/N-vd6he4nsZp-G3Plc4m6A

▍ 一扇窗子,開始自研元件

後來,我嘗試進一步深入使用RocketMQ。

  • 仿ONS風格封裝訊息SDK;
  • 運維側平滑擴容訊息佇列;
  • 生產環境DefaultMQPullConsumer消費模式嘗試

這些做完之後,我們又自研了註冊中心、配置中心,任務排程系統。設計這些系統的時候,從RocketMQ原始碼裡汲取了很多的營養,雖然現在看來有很多設計不完善的地方,程式碼質量也有待提高,但做完這些系統後,還是大大提升我的自信心。

RocketMQ給我開啟了一扇窗子,讓我能看到更廣闊的Java世界。 對我而言,這就是開源的盛宴

4.2 Kafka: 大資料生態的不可或缺的部分

Kafka是一個擁有高吞吐、可持久化、可水平擴充套件,支援流式資料處理等多種特性的分散式訊息流處理中介軟體,採用分散式訊息釋出與訂閱機制,在日誌收集、流式資料傳輸、線上/離線系統分析、實時監控等領域有廣泛的應用。

▍ 日誌同步

在大型業務系統設計中,為了快速定位問題,全鏈路追蹤日誌,以及故障及時預警監控,通常需要將各系統應用的日誌集中分析處理。

Kafka設計初衷就是為了應對大量日誌傳輸場景,應用通過可靠非同步方式將日誌訊息同步到訊息服務,再通過其他元件對日誌做實時或離線分析,也可用於關鍵日誌資訊收集進行應用監控。

日誌同步主要有三個關鍵部分:日誌採集客戶端,Kafka訊息佇列以及後端的日誌處理應用。

  1. 日誌採集客戶端,負責使用者各類應用服務的日誌資料採集,以訊息方式將日誌“批量”“非同步”傳送Kafka客戶端。
    Kafka客戶端批量提交和壓縮訊息,對應用服務的效能影響非常小。
  2. Kafka將日誌儲存在訊息檔案中,提供持久化。
  3. 日誌處理應用,如Logstash,訂閱並消費Kafka中的日誌訊息,最終供檔案搜尋服務檢索日誌,或者由Kafka將訊息傳遞給Hadoop等其他大資料應用系統化儲存與分析。

日誌同步示意圖:

流計算處理

在很多領域,如股市走向分析、氣象資料測控、網站使用者行為分析,由於資料產生快、實時性強且量大,您很難統一採集這些資料並將其入庫儲存後再做處理,這便導致傳統的資料處理架構不能滿足需求。Kafka以及Storm、Samza、Spark等流計算引擎的出現,就是為了更好地解決這類資料在處理過程中遇到的問題,流計算模型能實現在資料流動的過程中對資料進行實時地捕捉和處理,並根據業務需求進行計算分析,最終把結果儲存或者分發給需要的元件。

▍ 資料中轉樞紐

近10多年來,諸如KV儲存(HBase)、搜尋(ElasticSearch)、流式處理(Storm、Spark、Samza)、時序資料庫(OpenTSDB)等專用系統應運而生。這些系統是為單一的目標而產生的,因其簡單性使得在商業硬體上構建分散式系統變得更加容易且價效比更高。通常,同一份資料集需要被注入到多個專用系統內。例如,當應用日誌用於離線日誌分析時,搜尋單個日誌記錄同樣不可或缺,而構建各自獨立的工作流來採集每種型別的資料再匯入到各自的專用系統顯然不切實際,利用訊息佇列Kafka版作為資料中轉樞紐,同份資料可以被匯入到不同專用系統中。

下圖是美團 MySQL 資料實時同步到 Hive 的架構圖,也是一個非常經典的案例。

4.3 如何技術選型

2018年去哪兒QMQ開源了,2019年騰訊TubeMQ開源了,2020年Pulsar如火如荼。

訊息佇列的生態是如此的繁榮,那我們如何選型呢?

我想我們不必侷限於訊息佇列,可以再擴大一下。簡單談一談我的看法。

Databases are specializing – the “one size fits all” approach no longer applies ----- MongoDB設計哲學

第一點:先有場景,然後再有適配這種場景的技術。什麼樣的場景選擇什麼樣的技術。

第二點:現實往往很複雜,當我們真正做技術選型,並需要落地的時候,技術儲備成本是兩個我們需要重點考量的因素。

▍ 技術儲備

  • 技術團隊有無使用這門技術的經驗,是否踩過生產環境的坑,以及針對這些坑有沒有完備的解決方案;
  • 架構團隊是否有成熟的SDK,工具鏈,甚至是技術產品。

▍ 成本

  • 研發,測試,運維投入人力成本;
  • 伺服器資源成本;
  • 招聘成本等。

最後一點是的因素,特別是管理者的因素。每一次大的技術選型考驗技術管理者的視野,格局,以及管理智慧。

5 寫到最後

我覺得這個世界上沒有什麼毫無道理的橫空出世,真的,如果沒有大量的積累大量的思考是不會把事情做好的。。。
總之,在經歷了這部電影以後,我覺得我要學的太多了,這世界上有太多的能人,你以為的極限,弄不好,只是別人的起點。所以只有不停地進取,才能不丟人。那,人可以不上學,但一定要學習,真的。
------ 韓寒《後會無期》演講

我學習訊息佇列的過程是不斷思考,不斷實踐的過程,雖然我以為的極限,弄不好,只是別人的起點,但至少現在,當我面對這門技術的時候,我的內心充滿了好奇心,同時也是無所畏懼的。

我始終相信:每天學習一點點,比昨天進步一點點就好。


如果我的文章對你有所幫助,還請幫忙點贊、在看、轉發一下,你的支援會激勵我輸出更高質量的文章,非常感謝!

相關文章