dubbo客戶端

yeohx發表於2018-11-07

dubbo客戶端:

根據配置檔案請求服務端

查詢服務端方式:直接查詢、註冊中心查詢

直接查詢:在配置檔案中直接配置服務端地址和實現介面 在沒有註冊中心,直連提供者的情況下(例如:<dubbo:reference url="dubbo://service-host/com.foo.FooService?version=1.0.0" />),ReferenceConfig 解析出的 URL 的格式為:dubbo://service-host/com.foo.FooService?version=1.0.0。 基於擴充套件點自適應機制,通過 URL 的 dubbo:// 協議頭識別,直接呼叫 DubboProtocol 的 refer() 方法,返回提供者引用。

 註冊中心查詢:通過註冊中心找到服務端地址和實現介面 在有註冊中心,

1、通過註冊中心發現提供者地址的情況下 (例如:<dubbo:registry address="zookeeper://10.20.153.10:2181" />),ReferenceConfig 解析出的 URL 的格式為: registry://registry-host/com.alibaba.dubbo.registry.RegistryService?refer=URL.encode("consumer://consumer-host/com.foo.FooService?version=1.0.0")。 2、基於擴充套件點自適應機制,通過 URL 的 registry:// 協議頭識別,就會呼叫 RegistryProtocol 的 refer() 方法,基於 refer 引數中的條件,查詢提供者 URL,如: dubbo://service-host/com.foo.FooService?version=1.0.0。 

3、基於擴充套件點自適應機制,通過提供者 URL 的 dubbo:// 協議頭識別,就會呼叫 DubboProtocol 的 refer() 方法,得到提供者引用。 然後 RegistryProtocol 將多個提供者引用,通過 Cluster 擴充套件點,偽裝成單個提供者引用返回。

客戶端消費過程:

dubbo客戶端

1、首先 ReferenceConfig 類的 init 方法呼叫 Protocol 的 refer 方法生成 Invoker 例項(如上圖中的紅色部分),這是服務消費的關鍵。

2、接下來把 Invoker 轉換為客戶端需要的介面(如:HelloWorld)。 關於每種協議如 RMI/Dubbo/Web service 等它們在呼叫 refer 方法生成 Invoker 例項:

Dubbo 的實現 Dubbo 協議的 Invoker 轉為 Exporter 發生在 DubboProtocol 類的 export 方法,它主要是開啟 socket 偵聽服務,並接收客戶端發來的各種請求,通訊細節由 Dubbo 自己實現。 

RMI 的實現 RMI 協議的 Invoker 轉為 Exporter 發生在 RmiProtocol類的 export 方法,它通過 Spring 或 Dubbo 或 JDK 來實現 RMI 服務,通訊細節這一塊由 JDK 底層來實現,這就省了不少工作量。

invoker是什麼?

dubbo客戶端

結合服務消費和提供者的程式碼示例來進行說明: 

 服務消費者程式碼: 

 public class DemoClientAction {

 private DemoService demoService; 

 public void setDemoService(DemoService demoService) {

      this.demoService = demoService; 

 } 

 public void start() {

      String hello = demoService.sayHello("world" + i); 

    } 

}

上面程式碼中的 DemoService 就是上圖中服務消費端的 proxy,使用者程式碼通過這個 proxy 呼叫其對應的 Invoker(DubboInvokerHessianRpcInvokerInjvmInvokerRmiInvokerWebServiceInvoker 中的任何一個),而該 Invoker 實現了真正的遠端服務呼叫。

 服務提供者程式碼: 

 public class DemoServiceImpl implements DemoService { 

     public String sayHello(String name) throws RemoteException {

         return "Hello " + name;

     }

 } 

上面這個類會被封裝成為一個 AbstractProxyInvoker 例項,並新生成一個 Exporter 例項。這樣當網路通訊層收到一個請求後,會找到對應的 Exporter 例項,並呼叫它所對應的 AbstractProxyInvoker 例項,從而真正呼叫了服務提供者的程式碼。Dubbo 裡還有一些其他的 Invoker 類,但上面兩種是最重要的。


相關文章