1. 程式人生 > >Java系統和PHP系統相互呼叫

Java系統和PHP系統相互呼叫

一、HTTP JSON方式的缺點

  1. JSON序列化效率低
  2. 多語言服務治理功能低

二、關於RPC框架

RPC 框架大致分為兩類,一種是偏重服務治理,另一種側重跨語言呼叫

2.1 服務治理型

特點

功能豐富,提供高效能的遠端呼叫、服務發現及服務治理能力,適用於大型服務的服務解耦及服務治理,對於特定語言(Java)的專案可以實現透明化接入。缺點是語言耦合度較高,跨語言支援難度較大。

常用框架

  • Dubbo
  • Motan

    2.2 跨語言呼叫型

    特點

    側重於服務的跨語言呼叫,能夠支援大部分的語言進行語言無關的呼叫,非常適合多語言呼叫場景。但這類框架沒有服務發現相關機制,實際使用時需要代理層進行請求轉發和負載均衡策略控制。

    常用框架

  • Thrift
  • gRPC

三、如何提供服務給PHP系統

Dubbo(阿里開源)

特點

可以實現php呼叫php,php呼叫java(dubbo),java(dubbo)呼叫php,Java調Java,真正的跨語言

缺點

開發活躍程度極低,社群小,資料少,沒有release版本

3.2 Dubbo Restful(合併自Dubbox)

特點

顯著簡化企業內部的異構系統之間的(跨語言)呼叫。

服務消費場景:

  1. 非dubbo的消費端呼叫dubbo的REST服務(non-dubbo --> dubbo)
  2. dubbo消費端呼叫dubbo的REST服務 (dubbo --> dubbo)
  3. dubbo的消費端呼叫非dubbo的REST服務 (dubbo --> non-dubbo)
問題
  1. Dubbo REST的服務能和Dubbo註冊中心、監控中心整合嗎?

    可以的,而且是自動整合的,也就是你在dubbo中開發的所有REST服務都會自動註冊到服務冊中心和監控中心,可以通過它們做管理。
    但是,只有當REST的消費端也是基於dubbo的時候,註冊中心中的許多服務治理操作才能完全起作用。而如果消費端是非dubbo的,自然不受註冊中心管理,所以其中很多操作是不會對消費端起作用的。

  2. Dubbo REST中如何實現負載均衡和容錯(failover)?

    如果dubbo REST的消費端也是dubbo的,則Dubbo REST和其他dubbo遠端呼叫協議基本完全一樣,由dubbo框架透明的在消費端做load balance、failover等等。
    如果dubbo REST的消費端是非dubbo的,甚至是非java的,則最好配置服務提供端的軟負載均衡機制,目前可考慮用LVS、HAProxy、 Nginx等等對HTTP請求做負載均衡。

    montan(微博開源)

    Java系統使用motan提供服務,php系統使用Motan-PHP(PHP client)呼叫服務。

    特點

    motan暫不支援以服務注入方式引用yar 服務(使用motan作為yar client)。
    目前yar協議主要解決java與php互通的問題,當java作為服務端,php作為client端,php可以在不做任何修改的情況下通過yar 協議使用java的服務。
    而使用php做server、java做client的場景下(一般這種場景比較少),php的yar server不支援註冊服務等功能,所以java作為client 時也沒有必要通過motan呼叫服務。yarclient是個單獨的小模組,是個類似httpclient這樣的簡易客戶端,只能通過域名或ip訪問yar服務。

    缺點

    只支援PHP系統呼叫Java系統,沒有stable release版本,文件很少,社群小,開發活躍程度低。整體不如Dubbo+dubbo-php-framework方式

    模仿Dubbo Restful,很類似,從文件上對比,不如Dubbo Restful

    3.5 Client + Agent(還未完全開源)

    大概是使用motan + motan-go(agent)等實現。朝著weibo mesh的服務化方向,將 Motan Agent定位為統一服務管理的執行節點。

    實現方式

    為不同語言提供非常輕量的 Client,只實現與 Agent 的互動和必要的請求序列化能力;提供一個 local 的 Agent 代理,能夠提供不同 RPC 協議互動能力,以及統一的服務治理能力與標準,服務治理的絕大部分功能都在語言無關的 Agent 中實現。通過使用 Agent,可以為類似 PHP 這樣的解釋型語言提供長連結複用能力,提高請求效能。

四、跨語言服務化

阿里Dubbo和微博motan都稱自己框架有多語言服務化功能,都在開發中,都還不夠成熟

4.1 挑戰

HTTP RESTful API

HTTP 本身就是語言無關的協議,一般由服務提供方與使用方通過文件來進行服務約定。這也是目前使用非常廣泛的跨語言互動方式,HTTP服務的服務治理能力一般依賴於代理層和服務呼叫方自己實現,一般代理服務需要單獨部署,所有請求流量經由代理服務進行轉發。例如使用 nginx 提供基礎的負載均衡與流量控制等治理能力就是最簡單的跨語言服務治理方案。

HTTP的跨語言服務化,有些方案選擇了為特定語言實現強大服務治理能力,對其他語言提供相容能力,例如Spring Cloud為Java 服務提供完整的服務治理能力,包括服務發現、路由器、過濾器、配置管理、熔斷器等等。但很難為不同語言提供統一的服務治理能力,特別是在 Client 側的一些服務治理能力,不同語言都需要做相同功能的開發。

還有一些方案使用本機代理的方式,例如envoy、linkerd等可以部署到單機的 HTTP 代理服務,在代理服務中整合統一服務發現與治理能力。這種方案能夠做到不同語言的Client和 Server 都提供相同的服務治理能力,但服務治理的功能很難做到前一種方案那麼強大。

RPC

使用 RPC 作為服務呼叫方式時,跨語言與服務治理也很難同時滿足,對於跨語言型的 RPC 協議,例如 gRPC 等,都能夠提供不同語言互動的能力,但是相關的服務治理功能還沒有那麼完善,做到了’互動’,但還無法做到’治理’。使用跨語言型 RPC 框架時一般會選擇使用 HTTP(HTTP2)作為通訊協議,這樣可以直接應用 HTTP 方式的服務治理功能;

對於服務治理型RPC,由於選擇了在 Client 端進行服務發現與治理,如果要實現不同語言統一的服務治理能力,需要在不同語言的一側都實現相同的功能。實現起來也相當的困難。因此大部分服務治理型 RPC 專注與為特定語言提供完善的治理能力。

4.2 方式

1. 相容HTTP協議,增加HTTP RESTful協議

例如Dubbo Restful和motan Restful。這種方案將 Java 語言的 RPC 呼叫方式與其他語言獨立開來,只針對 Java Server 端提供,沒有為其他語言提供服務治理能力。由於只需要做 Java 協議的開發,這種方案研發和維護成本很低,不過能夠提供的統一服務治理能力就很低了。

2. 為不同語言提供RPC模組

例如Dubbo + dubbo-php-framework方式。這種方案能做到最貼近不同語言的使用習慣,可以為不同語言提供完全一致的服務治理能力,不論是作為 Server 端還是 Client 端。但這種方式也是成本最高的,包括開發不同語言的版本,以及後續的功能升級與版本維護代價都非常高。

3. 開發一個 Agent 模組,實現絕大部分的服務治理能力

例如motan Client + Agent方式。Agent在不同服務的Server或Client側執行。然後為不同語言開發一個很輕量的 Client 與 Agent 進行互動,由於 Client 只實現必要的互動功能,降低了不同語言版本的開發量與維護的成本。

五、可考慮的方案

  1. (如果是JSON效率低)考慮使用Google Protocol Buffers, thrift, Hessian等更高效序列化方式。
  2. (如果是服務治理功能低)保持原來HTTP+JSON方式不變,優化服務治理功能
  3. 自己基於已有開源框架二次開發(參考motan Client + Agent思路)
  4. 使用Dubbo Restful

六、參考資料

七、其他相關資料