IM開發基礎知識補課(九):想開發IM集羣?先搞懂什麼是RPC!

本文引用了後端技術指南針公衆號「淺談RPC那些事兒1」和即時通信網的「即時通信新手入門:快速理解RPC技術——基本概念、原理和用途」兩篇文章的部份內容。php

一、引言

常常有開發者在糾結怎麼開發IM集羣,雖然真正的使用人數,可能用我的電腦單機都能支撐。html

你也許會說,明明不須要用到IM集羣,幹嘛要自找麻煩?答曰:「老闆說這個得有!」、「萬一產品作成了,用戶量達到百萬、千萬級呢?」,各類回答,反此種種。總之,IM集羣就是得整一個(先甭管用不用的上...)。算法

固然,玩笑歸玩笑,真正要作到可投入到生產級別的IM集羣系統,難度仍是至關大的。必竟IM這種長鏈接應用相比傳統Http這種短鏈接應用太不標準。數據庫

咱們以一個典型的IM聊天消息傳輸爲例:apache

假設存在兩個正在聊天的用戶(用戶A和用戶B),當A鏈接的是IM集羣中的IM實例一、B鏈接的是IM集羣中的IM實例2,此時當用戶A向用戶B發送一條聊天消息時,這條消息應該如何傳遞呢?

咱們梳理一下上面這個例子的消息流轉過程:編程

  • 1)IM聊天消息首先會由用戶A發往IM實例1;
  • 2)IM實例1會將此條消息轉交給IM實例2;
  • 3)IM實例2會將此條消息最終投遞給鏈接在本實例上的用戶B。

如上述流程所示,這就是一個IM集羣系統中典型的聊天消息投遞過程。後端

那麼,這其中涉及到一個關鍵步驟:即第2)步中如何實現「IM實例1會將此條消息轉交給IM實例2」?緩存

此時,RPC技術出場了!安全

▲ 上圖是個典型的分佈式IM架構,注意中間的「RPC通訊」字樣(本圖引用自《基於Go的馬蜂窩旅遊網分佈式IM系統技術實踐》)服務器

本文將以通俗易懂的白話形式,幫你快速理解IM集羣中的關鍵技術——RPC。

推薦閱讀:另外一篇RPC基礎知識文章也值得一讀《即時通信新手入門:快速理解RPC技術——基本概念、原理和用途》。

本文已同步發佈於「即時通信技術圈」公衆號,歡迎關注:

▲ 本文在公衆號上的連接是:https://mp.weixin.qq.com/s/0RXTUWHXDmMddsPVWej2Qg

二、相關文章

▼ 如下兩篇文章有助於您對RPC和IM集羣有個初步的概念:

即時通信新手入門:快速理解RPC技術——基本概念、原理和用途》(推薦)
即時通信新手入門:一文讀懂什麼是Nginx?它可否實現IM的負載均衡?

▼ IM開發乾貨系列文章(本文是其第24篇):

IM消息送達保證機制實現(一):保證在線實時消息的可靠投遞
IM消息送達保證機制實現(二):保證離線消息的可靠投遞
如何保證IM實時消息的「時序性」與「一致性」?
IM單聊和羣聊中的在線狀態同步應該用「推」仍是「拉」?
IM羣聊消息如此複雜,如何保證不丟不重?
一種Android端IM智能心跳算法的設計與實現探討(含樣例代碼)
移動端IM登陸時拉取數據如何做到省流量?
通俗易懂:基於集羣的移動端IM接入層負載均衡方案分享
淺談移動端IM的多點登錄和消息漫遊原理
IM開發基礎知識補課(一):正確理解前置HTTP SSO單點登錄接口的原理
IM開發基礎知識補課(二):如何設計大量圖片文件的服務端存儲架構?
IM開發基礎知識補課(三):快速理解服務端數據庫讀寫分離原理及實踐建議
IM開發基礎知識補課(四):正確理解HTTP短鏈接中的Cookie、Session和Token
IM羣聊消息的已讀回執功能該怎麼實現?
IM羣聊消息到底是存1份(即擴散讀)仍是存多份(即擴散寫)?
IM開發基礎知識補課(五):通俗易懂,正確理解並用好MQ消息隊列
一個低成本確保IM消息時序的方法探討
IM開發基礎知識補課(六):數據庫用NoSQL仍是SQL?讀這篇就夠了!
IM裏「附近的人」功能實現原理是什麼?如何高效率地實現它?
IM開發基礎知識補課(七):主流移動端帳號登陸方式的原理及設計思路
IM開發基礎知識補課(八):史上最通俗,完全搞懂字符亂碼問題的本質
IM的掃碼登功能如何實現?一文搞懂主流應用的掃碼登錄技術原理
IM要作手機掃碼登錄?先看看微信的掃碼登陸功能技術原理
IM開發基礎知識補課(九):想開發IM集羣?先搞懂什麼是RPC!》(本文)

若是您是IM開發初學者,強烈建議首先閱讀《新手入門一篇就夠:從零開發移動端IM》。

三、正文概述

限於篇幅緣由,本文不會深刻展開RPC的底層技術原理,會盡可能用通俗白話的方式對概念性的東西進行講解。

經過本文你將主要了解到如下內容:

  • 1)什麼是RPC;
  • 2)爲何須要RPC;
  • 3)RPC的重要組件;
  • 4)常見RPC框架和各自特色。

四、什麼是RPC?

RPC 是1984年代由 Andrew D. Birrell & Bruce Jay Nelson 提出的(見二位大佬的論文《Implementing Remote Procedure Calls》),因此它並非最近纔有的技術概念。

關於RPC的介紹,正經的資料上大概是這樣介紹的:

RPC(Remote Procedure Call)遠程過程調用,它是一種經過網絡從遠程計算機程序上請求服務,而不須要了解底層網絡技術的協議。也就是說兩臺服務器A,B,一個應用部署在A服務器上,想要調用B服務器上應用提供的方法,因爲不在一個內存空間,不能直接調用,須要經過網絡來表達調用的語義和傳達調用的數據。

大白話理解RPC就是:RPC讓你用別人家的東西就像本身家的同樣。

看得我似懂非懂,因而我不得不問幾個問題:

  • 1)爲啥要用別人家的東西——請求其餘服務);
  • 2)我怎麼能夠借到別人家的東西——其餘服務調用;
  • 3)要是借用的話哪一種形式更好——肯定一個合適的調用方法);
  • 4)怎麼讓我用別人東西像本身的同樣——屏蔽底層細節透明通訊)。

在解答這些問題以前,咱們必須達到一個共識問題:RPC只是一種通訊模式,和http並不衝突對立,相反http能夠做爲RPC傳輸數據的一種協議,把RPC看成一種模式和思想,咱們才能更好地理解它。

更嚴謹的RPC基礎知識介紹,請閱讀:《即時通信新手入門:快速理解RPC技術——基本概念、原理和用途》。

五、爲何須要RPC?

以你們最熟悉的電商系統爲例,這樣規模的分佈式系統,須要拆分出用戶服務、商品服務、優惠券服務、支付服務、訂單服務、物流服務、售後服務等等。這些服務之間都相互調用,這時內部調用最好使用 RPC ,同時每一個服務均可以獨立部署,獨立上線。 

也就說當咱們的項目太大,須要解耦服務,擴展性強、部署靈活,這時就要用到 RPC ,這主要是解決了分佈式系統中,服務與服務之間的調用問題。

▲ 上圖中的分佈系統內部,就是用RPC實現的(本圖引用自《重新手到架構師,一篇就夠:從100到1000萬高併發的架構演進之路》)

對於IM集羣這樣的分佈式系統來講,不一樣IM實例間的用戶聊天消息,就是經過RPC進行流轉的。

六、爲何不直接使用HTTP,而要搞RPC?

在平常業務中咱們能夠把功能封裝成靜態庫、動態庫、sdk、獨立服務等,最多見也最方便的仍是HTTP這種形式的調用。

HTTP服務把須要提供的服務暴露成接口(也就是一般所說的http rest接口啦),使用方直接按約定的HTTP方法和URI進行數據交互。

咱們都知道HTTP協議是應用層協議,是個很是標準的協議,在HTTP協議之下還有網絡層、傳輸層、數據鏈路層等,一個數據包packet除了淨荷payload以外還有不少header,因爲標準和通用性的設計目標也使得HTTP一次數據交互真正傳輸的payload只是其中一部分。

HTTP是咱們用的最多最熟悉的交互模式,在系統內部各個服務之間接口較少,交互很少的狀況下工做得還不錯。

但若是在內部系統調用很複雜的前提下,HTTP調用的效率和安全性就不那麼理想了。

以IM系統爲例,單個IM實例的吞吐效率至少能夠達到幾萬甚至數十萬QPS,使用HTTP這種短鏈接(調用時創建socket鏈接,完成後釋放鏈接)方式顯的至關低效(每次調用都要從新經歷TCP的3次握手、4次揮手過程),在分佈式的狀況下勢必拉低整個IM集羣的吞吐效率。而對於RPC,這種socket長鏈接方式對於高性能場景來講,效果是顯而易見的。

更重要的是面對衆多的服務咱們須要的不只僅是一個通訊方式,而是一個內部服務的管理系統,這也就是咱們今天說的RPC框架。注意:RPC是一種模式策略和框架,並非單純的通訊協議。

題外話:實際上,HTTP在RPC系統中,並非個你死我活的關係,必竟HTTP只是個通訊協議,而HTTP有某些性能要求不敏感的場景來講,是徹底能夠做爲RPC的具體實現協議之一來使用的。

七、RPC的調用過程是什麼樣的?

▲ 典型的RPC調用過程

如上圖所示,一個典型的RPC調用過程是這樣(過程序號對應上圖中的數字):

  • 1)客戶端(client)以本地調用方式調用服務;
  • 2)客戶端存根(client stub)接收到調用後,負責將方法、參數等組裝成可以進行網絡傳輸的消息體(將消息體對象序列化爲二進制);
  • 3)客戶端經過 sockets 將消息發送到服務端;
  • 4)服務端存根(server stub)收到消息後進行解碼(將消息對象反序列化);
  • 5)服務端存根(server stub)根據解碼結果調用本地的服務;
  • 6)本地服務執行並將結果返回給服務端存根(server stub);
  • 7)服務端存根(server stub)將返回結果打包成消息(將結果消息對象序列化);
  • 8)服務端(server)經過 sockets 將消息發送到客戶端;
  • 9)客戶端存根(client stub)接收到結果消息,並進行解碼(將結果消息發序列化);
  • 10)客戶端(client)獲得最終結果。

RPC的做用,其實就是要把上述二、三、四、七、八、9 這些步驟都封裝起來。是否是很神奇?

八、關於HTTP和RPC的一些爭議

HTTP和RPC是兩個很容易混淆的概念,對於剛開始接觸RPC的人來講,一般都會困惑:有HTTP了爲何還要用RPC?

在知乎上看到了這個頗有趣的問題:《既然有http請求,爲何還要用rpc?

其中一個大佬的回答感受頗有意思: 

換個角度來講:HTTP 與 RPC 的關係就比如普通話與方言的關係。要進行跨企業服務調用時,每每都是經過 HTTP API,也就是普通話,雖然效率不高,可是通用,沒有太多溝通的學習成本。可是在企業內部仍是 RPC 更加高效,同一個企業公用一套方言進行高效率的交流,要比通用的 HTTP 協議來交流更加節省資源。整個中國有很是多的方言,正若有不少的企業內部服務各有本身的一套交互協議同樣。雖然國家一直在提倡使用普通話交流,可是這麼多年過去了,你回一趟家鄉探個親什麼的就會發現身邊的人仍是流行說方言。

若是再深刻一點說,普通話本質上也是一種方言,只不過它是官方的方言,使用最爲普遍的方言,相比而言其它方言都是小語種,小語種之中也會有幾個使用比較普遍比較特點的方言佔比也會比較大。這就比如開源 RPC 協議中 Protobuf 和 Thrift 同樣,它們兩應該是 RPC 協議中使用最爲普遍的兩個。

總之:RPC是一種編程模式和概念,並非很是具體的一種技術,實際上和HTTP沒有明確的衝突,HTTP能夠做爲RPC傳輸協議,緣由仍是RPCpid際上是一種內部服務框架而不是一個具體的通訊協議,它能夠涉及服務註冊、服務治理、服務發現、熔斷機制、負載均衡等。

九、典型的RPC框架

一個典型RPC框架中,包含了服務發現、負載、容錯、網絡傳輸、序列化等組件,其中「RPC 協議」就指明瞭程序如何進行網絡傳輸和序列化。

▲ 一個典型的 RPC 架構原理圖(本圖引用自《即時通信新手入門:快速理解RPC技術——基本概念、原理和用途》)

▲ 著名RPC框架Dubbo的架構圖(本圖引用自《即時通信新手入門:快速理解RPC技術——基本概念、原理和用途》)

一個 RPC 最重要的功能模塊,就是上圖中的」RPC 協議」部分: 

其中的序列化和反序列化的意思是:

  • 1)序列化:將數據結構或對象轉換成二進制串的過程;
  • 2)反序列化:將序列化中所生成的二進制串轉換成數據結構或者對象的過程。

在網絡消息傳輸中能夠基於TCP、UDP、http來實現,各自都有各自的特色。

基於 TCP 實現的 RPC 調用,可以靈活對協議字段進行定製,減小網絡開銷提升性能,實現更大的吞吐量和併發數,但要關注底層細節,在進行數據解析時更加複雜一些(好比最受歡迎的Protobuf的使用)。

基於 HTTP 實現的 RPC 可使用 JSON 和 XML 格式的請求或響應數據,解析工具很成熟,在其上進行二次開發會很是便捷和簡單。可是 HTTP 是上層協議,所佔用的字節數會比使用 TCP 協議傳輸所佔用的字節數更高。

對於其餘部分,本文再也不展開。

十、市面上常見的RPC框架及其特色

常見 RPC 技術和框架有:

  • 1)應用級的服務框架:阿里的 Dubbo/Dubbox、Google gRPC、Spring Boot/Spring Cloud。
  • 2)遠程通訊協議:RMI、Socket、SOAP(HTTP XML)、REST(HTTP JSON)。
  • 3)通訊框架:MINA 和 Netty。

目前流行的開源 RPC 框架仍是比較多的,有阿里巴巴的 Dubbo、Facebook 的 Thrift、Google 的 gRPC、Twitter 的 Finagle 等。

下面重點介紹當前最流行的三種RPC框架主要特色:

  • 1)gRPC:是 Google 公佈的開源軟件,基於最新的 HTTP 2.0 協議,並支持常見的衆多編程語言。RPC 框架是基於 HTTP 協議實現的,底層使用到了 Netty 框架的支持;
  • 2)Thrift:是 Facebook 的開源 RPC 框架,主要是一個跨語言的服務開發框架。用戶只要在其之上進行二次開發就行,應用對於底層的 RPC 通信等都是透明的。不過這個對於用戶來講須要學習特定領域語言這個特性,仍是有必定成本的;
  • 3)Dubbo:是阿里集團開源的一個極爲出名的 RPC 框架,在不少互聯網公司和企業應用中普遍使用。協議和序列化框架均可以插拔是極其鮮明的特點。

十一、本文小結

小結一下,簡單地理解RPC就是:

RPC 就是從一臺機器(客戶端)上經過參數傳遞的方式調用另外一臺機器(服務器)上的一個函數或方法(能夠統稱爲服務)並獲得返回的結果。

RPC 會隱藏底層的通信細節(不須要直接處理Socket通信或Http通信)。

RPC 是一個請求響應模型。客戶端發起請求,服務器返回響應(相似於Http的工做方式)。

RPC 在使用形式上像調用本地函數(或方法)同樣去調用遠程的函數(或方法)。

十二、參考資料

[1] 什麼是 RPC 框架

[2] 誰能用通俗的語言解釋一下什麼是 RPC 框架?

[3] 淺談RPC那些事兒[1]

[4] 即時通信新手入門:快速理解RPC技術——基本概念、原理和用途

[5] 即時通信新手入門:一文讀懂什麼是Nginx?它可否實現IM的負載均衡?

附錄:有關IM架構設計的文章

淺談IM系統的架構設計
簡述移動端IM開發的那些坑:架構設計、通訊協議和客戶端
一套海量在線用戶的移動端IM架構設計實踐分享(含詳細圖文)
一套原創分佈式即時通信(IM)系統理論架構方案
從零到卓越:京東客服即時通信系統的技術架構演進歷程
蘑菇街即時通信/IM服務器開發之架構選擇
騰訊QQ1.4億在線用戶的技術挑戰和架構演進之路PPT
微信後臺基於時間序的海量數據冷熱分級架構設計實踐
微信技術總監談架構:微信之道——大道至簡(演講全文)
如何解讀《微信技術總監談架構:微信之道——大道至簡》
快速裂變:見證微信強大後臺架構從0到1的演進歷程(一)
17年的實踐:騰訊海量產品的技術方法論
移動端IM中大規模羣消息的推送如何保證效率、實時性?
現代IM系統中聊天消息的同步和存儲方案探討
IM開發基礎知識補課(二):如何設計大量圖片文件的服務端存儲架構?
IM開發基礎知識補課(三):快速理解服務端數據庫讀寫分離原理及實踐建議
IM開發基礎知識補課(四):正確理解HTTP短鏈接中的Cookie、Session和Token
WhatsApp技術實踐分享:32人工程團隊創造的技術神話
微信朋友圈千億訪問量背後的技術挑戰和實踐總結
王者榮耀2億用戶量的背後:產品定位、技術架構、網絡方案等
IM系統的MQ消息中間件選型:Kafka仍是RabbitMQ?
騰訊資深架構師乾貨總結:一文讀懂大型分佈式系統設計的方方面面
以微博類應用場景爲例,總結海量社交系統的架構設計步驟
快速理解高性能HTTP服務端的負載均衡技術原理
子彈短信光鮮的背後:網易雲信首席架構師分享億級IM平臺的技術實踐
知乎技術分享:從單機到2000萬QPS併發的Redis高性能緩存實踐之路
IM開發基礎知識補課(五):通俗易懂,正確理解並用好MQ消息隊列
微信技術分享:微信的海量IM聊天消息序列號生成實踐(算法原理篇)
微信技術分享:微信的海量IM聊天消息序列號生成實踐(容災方案篇)
新手入門:零基礎理解大型分佈式架構的演進歷史、技術原理、最佳實踐
一套高可用、易伸縮、高併發的IM羣聊、單聊架構方案設計實踐
阿里技術分享:深度揭祕阿里數據庫技術方案的10年變遷史
阿里技術分享:阿里自研金融級數據庫OceanBase的艱辛成長之路
社交軟件紅包技術解密(一):全面解密QQ紅包技術方案——架構、技術實現等
社交軟件紅包技術解密(二):解密微信搖一搖紅包從0到1的技術演進
社交軟件紅包技術解密(三):微信搖一搖紅包雨背後的技術細節
社交軟件紅包技術解密(四):微信紅包系統是如何應對高併發的
社交軟件紅包技術解密(五):微信紅包系統是如何實現高可用性的
社交軟件紅包技術解密(六):微信紅包系統的存儲層架構演進實踐
社交軟件紅包技術解密(七):支付寶紅包的海量高併發技術實踐
社交軟件紅包技術解密(八):全面解密微博紅包技術方案
社交軟件紅包技術解密(九):談談手Q紅包的功能邏輯、容災、運維、架構等
社交軟件紅包技術解密(十):手Q客戶端針對2020年春節紅包的技術實踐
即時通信新手入門:一文讀懂什麼是Nginx?它可否實現IM的負載均衡?
即時通信新手入門:快速理解RPC技術——基本概念、原理和用途
多維度對比5款主流分佈式MQ消息隊列,媽媽不再擔憂個人技術選型了
從游擊隊到正規軍(一):馬蜂窩旅遊網的IM系統架構演進之路
從游擊隊到正規軍(二):馬蜂窩旅遊網的IM客戶端架構演進和實踐總結
IM開發基礎知識補課(六):數據庫用NoSQL仍是SQL?讀這篇就夠了!
瓜子IM智能客服系統的數據架構設計(整理自現場演講,有配套PPT)
阿里釘釘技術分享:企業級IM王者——釘釘在後端架構上的過人之處
從游擊隊到正規軍(三):基於Go的馬蜂窩旅遊網分佈式IM系統技術實踐
微信後臺基於時間序的新一代海量數據存儲架構的設計實踐
IM開發基礎知識補課(九):想開發IM集羣?先搞懂什麼是RPC!
>>  更多同類文章 ……

(本文同步發佈於:http://www.52im.net/thread-2996-1-1.html

相關文章
相關標籤/搜索