dubbo是如何实现的微内核呢函数
dubbo定义了规则,使用的都是spi的扩展机制,盗用一张图能够看到spa
![]() |
从上边能够看出来,dubbo不实现组件,使用的都是spi的扩展,这样实现微内核,可扩展。对象
加载组件使用的是 SpiExtensionFactory 和 SpringExtensionFactory 两种方式;blog
而后经过adaptive加载 默认的实现类,若是有的此注解;接口
默认适应扩展 :被 @SPI("abc") 注解的 Interface , 那么这个扩展点的缺省适应扩展就是 SPI 配置文件中 key 为 "abc" 的扩展。若是存在被 @Adaptive 注解在类上的扩展点接口实现 ,那么这个类就做为扩展点的缺省适应扩展, 一个扩展点只能有一个缺省适应扩展也就是说多个扩展中只能有一个在类上被 @Adaptive 注解,若是有多个 dubbo 会抛出 IllegalStateException("More than 1 adaptive class found : ")。ci
@SPI (注解在类上) : @SPI 注解标识了接口是一个扩展点 , 属性 value 用来指定默认适配扩展点的名称。@Activate (注解在类型和方法上) : @Activate 注解在扩展点的实现类上 ,表示了一个扩展类被获取到的的条件,符合条件就被获取,不符合条件就不获取 ,根据 @Activate 中的 group 、 value 属性来过滤 。具体参考 ExtensionLoader 中的 getActivateExtension 函数。get
@Adaptive (注解在类型和方法上) : @Adaptive 注解在类上 , 这个类就是缺省的适配扩展。@Adaptive 注解在扩展点 Interface 的方法上时 , dubbo 动态的生成一个这个扩展点的适配扩展类(生成代码 ,动态编译实例化 Class ),名称为 扩展点 Interface 的简单类名 + $Adaptive ,例如 :ProxyFactory$Adpative 。这么作的目的是为了在运行时去适配不一样的扩展实例 , 在运行时经过传入的 URL 类型的参数或者内部含有获取 URL 方法的参数 ,从 URL 中获取到要使用的扩展类的名称 ,再去根据名称加载对应的扩展实例 ,用这个扩展实例对象调用相同的方法 。若是运行时没有适配到运行的扩展实例 , 那么就使用 @SPI 注解缺省指定的扩展。经过这种方式就实现了运行时去适配到对应的扩展。io
ExtensionLoader.getExtensionLoader(Xxx.class).getExtension(extName);编译
ExtendionLoader 是 实现spi的核心,加载扩展点的顺序是,首先找adaptive的扩展实例,没有则自动生成一个扩展实例table
参考: 黑帽子技术 https://mp.weixin.qq.com/s/McjABJcRBaJnRv9aWQr0FQ