事務消息介紹
事務消息貌似是阿里提出的分佈式事務解決方案,依賴於RocketMQ的事務消息實現(RocketMQ事務消息)。
其核心是通過MQ類似於DB的事務提交或回滾功能+MQ主動回查機制(MQ請求應用)來確保最終的消息確認動作。
它的實現原理也比較簡單,我們可以基於上一篇“分佈式事務(四):本地消息表”對照理解。
在本地消息表實現方案中,由於MQ不支持(或者不使用)事務,我們無法確保最終消息投遞結果和數據庫事務是否保持一致,所以加入了定時任務+本地消息表來進行消息重發機制保障最終一致性。
但是這樣使每個服務都存在定時任務和消息表,導致代碼邏輯以及數據庫表設計和業務耦合嚴重;所以在事務消息中,將這一部分功能交給MQ進行實現。
MQ事務消息
RocketMQ是支持事務的,其實現原理也是二階段提交。
也就是說我先發起一個發送消息的動作,但是這個動作類似於db中的聲明瞭一個事務並執行了sql,此時並沒有確認提交或者回滾。 然後進行業務處理,處理成功這提交,失敗則回滾。
事務消息的回查機制
事務消息回查機制是指,假設客戶端發起了一個發送消息的動作,但是後續沒響兒了;那MQ怎麼辦呢,也不能傻等着。
所以MQ就主動的請求服務發起方,來進行詢問;這個就是回查機制。
回查機制需要服務發起方進行接口的提供。
事務消息模型
這裏畫了一個事務消息大致流程:
我們跟着圖來解讀一下:
- 在事務消息流程中我們將消息發送功能前置,即上圖的步驟1,這個時候發送的消息並沒進行確認;但是一定要保證發送成功。
- 接下來做業務操作,即上圖步驟2;出錯了DB就回滾也沒事。
- 如果第二步成功,則給MQ發送確認提交動作,即步驟3;表示步驟1的消息已經確認發送。如果在這一步出現了錯誤(比如“本地消息表”方案中的MQ請求超時等)也沒有關係。
- 爲什麼第二步第三步中出錯了也沒有關係呢,這個時候就用到了RocketMQ的回查機制,通過MQ主動回查應用接口,確認以上業務動作是否成功。
- 子服務處理完成,通過同樣的方式確保通知回調。
在以上流程中,需要對MQ進行2次請求,並且業務方需要在應用中加入一個供MQ回查的接口。
事務消息和其他解決方案對比
- 事務消息和本地消息表一樣,在消費方異常的情況下,都是對一個接口進行冪等性多次重試最終達到一致性。
- 相較於TCC或者SAGA沒有過多的業務邏輯。
- 理論上來說,服務方也存在多次消費失敗的情況,這還是需要人工介入。
- 人工介入流程不管是TCC、SAGA、還是本地消息表都在理論上無法避免。
事務消息的優點
- 相較於TCC,無需進行確認資源以及提交回滾操作,在邏輯上很簡單。
- 相較於SAGA,也無需進行正向和逆向補償。
- 且TCC和SAGA也需要有全局事務協調者的存在,而事務消息中MQ相當於承擔了這一角色。
- 相較於本地事務表,消息獨立存儲,無耦合表結構,業務方代碼、表都更純粹。
- 提供了回查機制保障最終消息確認。
事務消息的缺點
好像沒啥缺點,如果非要說有:
- 消息發送需要兩次通信。
- 代碼中會多加入一個供MQ回查的接口。 有點吹毛求疵了?