上文分析了Dubbo服务发布的整体流程,但服务代理生成的具体细节介绍得还不是很详细。下面将会接着上文继续分析。上文介绍了服务代理生成的切入点,如下:
|
|
这里的proxyFactory是在ServiceConfig中定义的,是final类型静态变量,赋值后无法进行修改。如下:
|
|
proxyFactory通过ExtensionLoader拓展机制进行加载。查看ProxyFactory接口源码如下:
|
|
ProxyFactory接口有三个实现类,分别为JavassistProxyFactory、JdkProxyFactory、StubProxyFactoryWrapper。其中JavassistProxyFactory、JdkProxyFactory作为代理工厂,StubProxyFactoryWrapper实现了对代理工厂进行装饰的功能。在Dubbo中通过SPI配置默认的代理工厂为JavassistProxyFactory(具体是如何实现配置的,这里就不讲了,详见Dubbo SPI拓展机制)。
下面来重点看看JavassistProxyFactory代理工厂。
JavassistProxyFactory继承实现关系图如下:
JavassistProxyFactory源码非常简单,只有两个方法:
|
|
其中getProxy是实现抽象类AbstractProxyFactory中的抽象方法。AbstractProxyFactory抽象类实现了ProxyFactory接口中getProxy方法,JdkProxyFactory也实现了抽象类AbstractProxyFactory中的getProxy抽象方法。Javassist与Jdk动态代理的共同部分被封装在父类AbstractProxyFactory中,具体的实现类只需负责实现代理生成过程的差异化部分。
其中getInvoker方法是在ProxyFactory接口中定义的,用于创建Invoker。getInvoker中代码很简单,直接返回一个匿名类。匿名类继承了AbstractProxyInvoker抽象类,AbstractProxyInvoker抽象类又实现了Invoker接口,即表明改匿名类实现了Invoker接口,匿名类是封装了服务提供者的调用者。
Invoker接口定义了一个泛型。定义的方法很简单,只有两个方法,如下:
|
|
抽象类AbstractProxyInvoker实现了Invoker接口,AbstractProxyInvoker定义属性和构造方法如下:
|
|
- proxy:是final类型变量,指向服务提供者
- type:是final类型变量,服务的接口类型
- url:是final类型变量,携带服务地址、端口等多种信息的自定义URL对象
构造方法主要对输入参数做一些校验,然后将输入参数值直接赋值给定义属性,赋值后定义属性值将不可更改。
AbstractProxyInvoker也实现了invoker方法。方法内部很简单,直接通过RpcResult创建一个对象即可,创建RpcResult时的构建参数是通过方法doInvoke生成的。如下:
|
|
这里的doInvoke方法是抽象方法,由子类实现。抽象方法定义如下:
|
|
在ProxyFactory接口JavassistProxyFactory实现类中,getInvoker方法内部通过匿名内部类实现了doInvoke抽象方法。
Result接口主要定义了RPC 调用的相关方法,如下:
|
|
RpcResult是对Result接口的一个实现。可看作对传入对象Object的一个包装,部分源码如下:
|
|
本节介绍了Dubbo服务发布的Invoker生成过程,下节将继续分析Dubbo服务发布的服务暴露过程