
DUBBO泛化调用原理与设计思想
编者荐语:
不是很多人在用的Dubbo了,但是调用原理还是要知道的
1 泛化调用实例
对于JAVA服务端开发者而言在使用Dubbo时并不经常使用泛化调用,通常方法是在生产者发布服务之后,消费者可以通过引入生产者提供的client进行调用。那么泛化调用使用场景是什么呢?
第一种场景是消费者不希望引入生产者提供的client依赖,只希望关注调用哪个方法,需要传什么参数即可。第二种场景是消费者不是使用Java语言,而是使用例如Python语言,那么如何调用使用Java语言生产者提供的服务呢?这时我们可以选择泛化调用。
泛化调用使用方法并不复杂,下面我们编写一个泛化调用实例。首先生产者发布服务,这与普通服务发布没有任何区别。
Person类声明:
provider.xml文件内容:
消费者代码有所不同:
2 Invoker
我们通过源码分析讲解泛化调用原理,首先需要了解Invoker这个Dubbo重量级概念。
在生产者暴露服务流程总体分为两步,第一步是接口实现类转换为Invoker,第二步是Invoker转换为Exporter并放入ExporterMap,我们首先分析生产者暴露服务流程:
生产者通过ProxyFactory.getInvoker方法创建Invoker(AbstractProxyInvoker):
我们再分析消费者引用服务流程:
消费者Invoker通过显示实例化创建,例如本地暴露和远程暴露都是通过显示初始化的方法创建Invoker(AbstractInvoker):
再通过ProxyFactory.getProxy创建代理:
无论是生产者还是消费者的Invoker都实现自org.apache.dubbo.rpc.Invoker:
3 责任链模式
为什么生产者和消费者都要转换为Invoker,而不是不直接调用呢?我认为Invoker正是Dubbo设计精彩之处:真实调用都转换为Invoker,这样就可以通过责任链模式增强Invoker功能。
无论是生产者还是消费者都会创建过滤器链,我们看看buildInvokerChain这个方法:
加载所有包含Activate注解的过滤器,根据group过滤得到过滤器列表,Invoker最终被放到过滤器链尾部,生产者最终生成链路:
消费者最终生成链路:
4 泛化调用原理
我们终于看到了泛化调用核心原理,在生产者链路看到GenericFilter过滤器,消费者链路看到GenericImplFilter过滤器,正是这两个过滤器实现了泛化调用。
(1) GenericImplFilter
(2) GenericFilter
5 文章总结
第一本文介绍了如何使用泛化调用,并引出泛化调用为什么生效这个问题。
第二本文介绍了重量级概念Invoker,并引出为什么Dubbo要创建Invoker这个问题。
第三通过源码分析知道了过滤器链增强了Invoker功能,并且是实现泛化调用的核心。
文章转载自公众号:Java极客技术
