MQ(消息隊列)常見的應用場景解析

前言

提升系統性能首先考慮的是數據庫的優化,以前一篇文章《數據庫的使用你可能忽略了這些》中有提到過開發中,針對數據庫須要注意的事項。可是數據庫由於歷史緣由,橫向擴展是一件很是複雜的工程,全部咱們通常會盡可能把流量都擋在數據庫以前。
不論是無限的橫向擴展服務器,仍是縱向阻隔到達數據庫的流量,都是這個思路。阻隔直達數據庫的流量,緩存組件和消息組件是兩大殺器。以前文章《Redis常見的應用場景解析》已經描述了最經常使用的緩存組件redis的應用場景,那麼今天,就重點說說MQ的應用場景。redis

MQ簡介

MQ,Message queue,消息隊列,就是指保存消息的一個容器。具體的定義這裏就不相似於數據庫、緩存等,用來保存數據的。固然,與數據庫、緩存等產品比較,也有本身一些特色,具體的特色後文會作詳細的介紹。
如今經常使用的MQ組件有activeMQ、rabbitMQ、rocketMQ、zeroMQ,固然近年來火熱的kafka,從某些場景來講,也是MQ,固然kafka的功能更增強大,雖然不一樣的MQ都有本身的特色和優點,可是,不論是哪一種MQ,都有MQ自己自帶的一些特色,下面,我們就先聊聊MQ的特色。數據庫

MQ特色

  • 先進先出
    不能先進先出,都不能說是隊列了。消息隊列的順序在入隊的時候就基本已經肯定了,通常是不需人工干預的。並且,最重要的是,數據是隻有一條數據在使用中。 這也是MQ在諸多場景被使用的緣由。
  • 發佈訂閱
    發佈訂閱是一種很高效的處理方式,若是不發生阻塞,基本能夠當作是同步操做。這種處理方式能很是有效的提高服務器利用率,這樣的應用場景很是普遍。
  • 持久化
    持久化確保MQ的使用不僅是一個部分場景的輔助工具,而是讓MQ能像數據庫同樣存儲核心的數據。
  • 分佈式
    在如今大流量、大數據的使用場景下,只支持單體應用的服務器軟件基本是沒法使用的,支持分佈式的部署,才能被普遍使用。並且,MQ的定位就是一個高性能的中間件。

應用場景

基於上文所述的特色,那麼MQ就衍生出了中的使用場景,在大型的系統中,應用很是普遍,這裏咱們就列舉一下常見的應用場景。緩存

應用解耦(異步)


系統之間進行數據交互的時候,在時效性和穩定性之間咱們都須要進行選擇。基於線程的異步處理,能確保用戶體驗,可是極端狀況下可能會出現異常,影響系統的穩定性,而同步調用不少時候沒法保證理想的性能,那麼咱們就能夠用MQ來進行處理。上游系統將數據投遞到MQ,下游系統取MQ的數據進行消費,投遞和消費能夠用同步的方式處理,由於MQ接收數據的性能是很是高的,不會影響上游系統的性能,那麼下游系統的及時率能保證嗎?固然能夠,否則就不會有下面的一個應用場景。服務器

通知

這裏就用到了前文一個重要的特色,發佈訂閱,下游系統一直在監聽MQ的數據,若是MQ有數據,下游系統則會按照 先進先出 這樣的規則, 逐條進行消費 ,而上游系統只須要將數據存入MQ裏,這樣就既下降了不一樣系統之間的耦合度,同時也確保了消息通知的及時性,並且也不影響上游系統的性能。微信

限流

上文有說了一個很是重要的特性,MQ 數據是隻有一條數據在使用中。 在不少存在併發,而又對數據一致性要求高,並且對性能要求也高的場景,如何保證,那麼MQ就能起這個做用了。無論多少流量進來,MQ都會讓你遵照規則,排除處理,不會由於其餘緣由,致使併發的問題,而出現不少意想不到髒數據。多線程

數據分發

MQ的發佈訂閱確定不是隻是簡單的一對一,一個上游和一個下游的關係,MQ中間件基本都是支持一對多或者廣播的模式,並且均可以根據規則選擇分發的對象。這樣上游的一份數據,衆多下游系統中,能夠根據規則選擇是否接收這些數據,這樣擴展性就很強了。
PS:上文中的上游和下游,在MQ更多的是叫作生產者(producer)和消費者(consumer)。架構

分佈式事務

分佈式事務是咱們開發中一直儘可能避免的一個技術點,可是,如今愈來愈多的系統是基於微服務架構開發,那麼分佈式事務成爲必需要面對的難題,解決分佈式事務有一個比較容易理解的方案,就是二次提交。基於MQ的特色,MQ做爲二次提交的中間節點,負責存儲請求數據,在失敗的狀況能夠進行屢次嘗試,或者基於MQ中的隊列數據進行回滾操做,是一個既能保證性能,又能保證業務一致性的方案,固然,這個方案的主要問題就是定製化較多,有必定的開發工做量。併發

應用示例

爲了更加直觀的展現MQ的應用場景,這裏咱們就用一個常見的電商系統中的幾個業務,來具體說明下MQ在實際開發中應用場景。
咱們的實際場景大概是一個基於微服務架構的電商系統,分爲用戶微服務、商品微服務、訂單微服務、促銷微服務等。基於微服務模式開發的系統,MQ的使用場景更多,下面咱們逐一說明:
一、註冊後咱們可能須要作不少初始化的操做,如:調用郵件服務器發送郵件、調用促銷服務贈送優惠劵、下發用戶數據到客戶關係系統等。那麼這時候咱們將這些操做去監聽MQ,當用戶註冊成功事後,經過MQ通知其餘業務進行操做。確保註冊用戶的性能。
二、後臺發佈商品的時候,商品數據須要從數據庫中轉換成搜索引擎數據(基於elasticsearch),那麼咱們應該將商品寫入數據庫後,再寫入到MQ,而後經過監聽MQ來生成elasticsearch對應的數據。
三、用戶下單後,24小時未支付,須要取消訂單。之前咱們多是定時任務循環查詢,而後取消訂單。實際上,我更推薦相似延遲MQ的方式,避免了不少無效的數據庫查詢,將一個MQ設置爲24小時後才讓消費者消費掉,這樣很大程度上能減輕服務器壓力。
四、支付完成後,須要及時的通知子系統(進銷存系統發貨,用戶服務積分,發送短信)進行下一步操做,可是,支付回調咱們都是須要保證高性能的,因此,我應該直接修改數據庫狀態,存入MQ,讓MQ通知子系統作其餘非實時的業務操做。這樣能保證核心業務的高效及時。異步

注意事項

其實,還有很是多的業務場景,是能夠考慮用MQ方式的,可是不少時候,也會存在濫用的狀況,咱們須要清楚認識咱們的業務場景:
發驗證碼短信、郵件,這種過度依賴外部,並且時效性能夠接收幾十秒延遲的,其實更好的方式是多線程異步處理,而不是過多依賴MQ。
秒殺搶購確保庫存不爲負數,更多的依賴高性能緩存(如redis),以及強制加鎖,千萬不要依賴消費者最終的返回結果。(實際工做中已經看到好幾個這樣的案例了)上游-下游 這種直接的處理方式效率確定是比 上游-MQ-下游 方式要高,MQ效率高,是由於,我只是上游-MQ 這個階段就當作已經成功了。elasticsearch

總結

任何一個技術的出現,都有他的業務場景,只有清楚技術的特色,才能更加貼切的挖掘出應用場景,深刻思考,深刻實踐才能將一個技術用在最合適的地方。


歡迎你們關注個人公衆號交流、學習、第一時間獲取最新的文章。
微信號:itmifen

相關文章
相關標籤/搜索