dubbo源码解读(二)dubbo-common之SPI机制
上一篇对解读dubbo做了简短的模块划分并且定义了阅读入口,这一次就针对dubbo-common来进行解读
1、首先来看个简单的东西, org.apache.dubbo.common.Version
进入源码看到有一个静态块,静态块内有一个校验类重复的校验,这里是避免引入2个dubbo版本引起问题做的检查,其他内部的实现相对简单容易理解
Version内定义了一个全局常量,这个是获取dubbo的版本使用的,由这里开始入手,可以发现会调用getVersion(Class<?> cls, String defaultVersion) 这里就是获取版本的核心区了,会发现 没有发现MANIFEST.MF 会去解析jar来完成版本解读
会发现这个类实际上东西很少,但是其实用价值很高。
2、SPI 不了解的可以百度然后你会发现很好玩的一样东西
java本身提供了SPI机制,SPI让插拔式编程变为了可能,这里就不详细累述了,我们来看下dubbo的SPI
dubbo的SPI位于org.apache.dubbo.common.extension包下
可以发现它提供了私有的构造函数,既然有私有的构造函数那么应该就有获取实例的静态方法,会发现getExtensionLoader(Class<T> type)
发现初始化的时候还会有一个初始化ExtensionFactory的操作,获取的最终期望的是AdaptiveExtension实例
继续往下阅读
这里有动态编译AdaptiveExtension实现类的方法
编译完成并实例化后会对其进行一次注入操作
这里是根据set方法进行注入同时加入DisableInject注解的不会进行注入操作
至此ExtensionLoader的初始化完成,了解了初始化的步骤,现在来看下dubbo是如何完成SPI初始化并且使用的
首先看下getExtension(String name) 这个方法
方法体内发现最终调用返回的是createExtension返回的结果
这里对于属性注入上边已经有进入过,我们不再进入,重点看下getExtensionClasses()
在这里考虑兼容原alibaba 所以又type.getName().replace("org.apache","com.alibaba")
关于strategies 这个是后边引入的,其特性就是为了一些自定义使用,不过针对dubbo 有设置默认值,
其中DUBBO_DIRECTORY 和DUBBO_INTERNAL_DIRECTORY 并没有任何分别,只是为了便于区分用户自己扩展和dubbo本身支持
这里就是加载接口和实现类的地方了
看到这里想到了ClassLoader ,这一部分后边会补充下,也作为对自己的学习理解使用
至此dubbo的SPI的基本功能也已经解读完成,也简单介绍下ExtensionFactory和Compiler
进入这两个里边会发现里边分别提供了针对这两个接口的实现,对于内部的细节,多数是一些技术上的东西,当然也有一些可以学习到的设计思想,不过在这里就不多做讲解,如果后边自己或者有其他人有需要,自己也可以考虑做下学习记录
这两个也是使用的SPI,其实无论是dubbo和spring 如果你在解读源码的时候,其实都会发现里边有SPI的身影,这也是插拔式编程的强大之处,它可以在你需要某个功能接口的时候加入,也可以在不需要的时候去掉它,但是在系统上的却不显出强依赖
下一篇针对dubbo-common 的URL设计做下学习了解