开发中的坑:MQ 也能做 RPC 调用?
hi, 大家好,我是 haohongfan。
最近瀏覽 帖子[1] 的時候看到一個有意思的吐槽。
大概意思是架構師沒有選用 RPC 框架來做服務間調用,而選擇用 MQ 來代替。是不是很意外?
當然不出意外的,評論區炸了!
現在提出一些疑問:
這個架構師的做法對嗎 ?
MQ 是否能做 RPC 調用 ?
RPC 框架的職責
回答上面問題之前,稍微捋一下 RPC 框架。目前市面上比較流行的 RPC 框架其實并不多。
Java: SpringCloud,Dubbo 等
Go: Dubbogo,go-micro,rpcx,go-zero 等
其他:Thrift,gRPC 等
當然還有其他的一些框架,這里就不再羅列。雖說 RPC 多如牛毛,但是大家干的事情基本都差不多,都是穩定,高效、準確的進行服務間遠程調用。
說起 RPC 應該大部分人下意識會聯想到 gRPC,不過 gRPC 只提供了服務間通信的能力,但卻沒有開源對應的服務治理的能力,需要進行二次開發。Thrift 也是同樣的問題。
下面以 Dubbogo 為例,大概介紹下 Dubbogo 實現的功能。
Dubbo-go 還有下面這些特點:
傳輸支持 http2
雙向流模式 rpc
應用級服務發現
跟 Dubbo(Java) 版本對齊,互相之間能穩定通信,同時也打通與其他微服務框架的通信,如:SpringCloud、gRPC
綜上,Dubbo-go 為了保證數據準確、高效、穩定傳輸,做了各種各樣的架構設計。隨著 dubbo 3.0 的發布,在易用性、超大規模微服務實踐、云原生基礎設施適配等幾大方向上進行了全面升級。
MQ 代替 RPC ?
接著說 MQ 是否能替代 RPC。先看看 MQ 被寫進八股文里面的幾大特性:
服務間解耦
最終一致性
流量削峰
異步消費
MQ 是微服務框架中必不可少的一環,上面的特性是我們日常開發中最常用的。這些特性確實能讓系統的穩定性得到增強,同時也讓系統的構建出現更多的可能性。
但是是否能讓 MQ 來代替 RPC,做服務間的調用?回答這個問題之前,我們再來看看 RPC 是如何工作的。
大概流程(資料節選 dubbogo website[2])
類似本地調用,Client 調用遠程服務
Client stub 收到調用,把調用方法、參數序列化
Client 通過 socket 把消息發送到服務端
Server stub 收到消息后,將消息對象反序列化
Server stub 根據解碼結果調用本地的服務,并將結果返回給 Server stub
Server stub 將返回結果序列化,通過 sockets 將消息發送到客戶端
Client stub 接收到結果消息,對返回消息反序列化
客戶端得到最終結果
簡單概括下 RPC 調用就是 Client 通過 TCP 調用 Server 的一個函數,得到一個返回結果。
再簡單點,是不是可以拆分下面兩個過程:
Client 發起一個調用到 Server
Server 返回一個結果到 Client
那么是不是可以用 MQ 模擬這個過程。
當然這個流程并不是我瞎寫的,這是 RabbitMQ 的官方教程 Remote procedure call (RPC)[3],有興趣的可以看文末的參考鏈接。
RabbitMQ tutorial 這篇文章基本就是 MQ 代替 RPC 的理論支持,所以文章開篇帖子提到的 Java 架構師的方案也不算無的放矢,也不算是錯的。
MQ 代替 RPC 的真實情況
正常情況有點規?;ヂ摼W公司內部都是會有一套 RPC 框架的,要么是基于開源版本的二次開發版本,要么完全自研的,使用過或者維護公司框架的都會被各種問題折磨到死,比如:限流、熔斷、重試、服務注冊發現、網絡問題,SDK 升級等。
如果能用 MQ 代替 RPC 做服務間調用,那是不是只用維護一套 MQ 基礎組件就可以了,既減少了人力的配置,又能將問題歸納。
理想很豐滿,真相往往卻很殘酷。
如果你下意識去搜一下:用 MQ 代替 RPC 進行服務間通信,你會發現網上只有寥寥幾個 Demo 而已,并沒有太多真實實踐。
沒有太多實踐 并不代表沒有人在項目中實戰過,比如那個 Java 架構師。曾經專門向朋友請教過這個設計,話說某大廠曾經在某個項目做了 MQ 代替 RPC 的實踐,但是三個月不到這個項目就被斃了。所以你看不到這個設計方案的缺點:因為很多人不能把失敗的案例放出來而已。
簡單說下這個方案的缺點吧:
本來 一次 TCP 通信就搞定的事情,用 MQ 后會被拆分成?四次 TCP,耗時增加不少。
目前 MQ 大部分消費端是 Pull 模型,有一定的耗時成本
服務間調用完全依賴于 MQ 的穩定性。從目前使用 MQ 經驗來看,MQ 穩定性的維護成本比 RPC 復雜太多了。如果做異步調用還能容忍出錯、延時,做同步調用的話,這些都是不能忽略的問題
如果用 MQ 代替 RPC,那些 RPC 框架做的服務治理的事情,MQ 都需要實現一遍,工作量并沒有減少
。。。
現在說一下統一結論:
用 MQ 代替 RPC 只是一種理論,但是高可用無法保障,而且對業務開發來說就更加黑盒了,出現問題就只能干瞪眼了,不建議業務開發實踐。
更多的坑,后續更新,歡迎關注公眾號。更多學習學習資料分享,關注公眾號:
參考資料
[1]
帖子: https://www.toutiao.com/w/a1702697615869956/
[2]dubbogo website: https://dubbo.apache.org/zh/blog/2019/01/07/%E6%B5%85%E8%B0%88-rpc/
[3]Remote procedure call (RPC): https://www.rabbitmq.com/tutorials/tutorial-six-python.html
總結
以上是生活随笔為你收集整理的开发中的坑:MQ 也能做 RPC 调用?的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 什么是 Go runtime.KeepA
- 下一篇: 如何有效控制 Go 线程数?