标签:面具 变化 ice png 标准 设置 name 试验 适应
JDK标准中SPI机制的一个问题就是其一次性实例化扩展点所有实现,如果有扩展实现初始化很耗时,但如果没用上也加载,会很浪费资源。Dubbo是如何解决该问题动态的选择具体的扩展点呢?使用@Adaptive。
查看@Adaptive注解源码及其注释,如下:
通过上面注释分析:如果不使用@Adaptive,使用@SPI标记的所有扩展均被默认加载;使用@Adaptive的扩展被选择加载,可以加载整个扩展点也可以加载该扩展点中某个功能点。(dubbo中所有的注册信息都是通过URL的形式进行处理的)
下面具体应用@Adaptive验证上述功能:
1、创建接口
增加传入URL参数的方法:
2、创建实现类
实现有参数URL的方法:
3、编写主程序
红框部分为自适应加载扩展点比默认加载所有扩展需要明确注意的:1)URL参数;2)明确地使用getAdaptiveE‘xtension加载自适应扩展。
在第一步接口中,需要增加@Adaptive。这里不直接添加,通过测试验证注解功能一步步添加。配置文件内容为:
1)修改@SPI注解为@SPI("hello")或者其他任意字符,执行前一篇文章中的主程序
执行结果:
对于非适应的加载,@SPI是否指定默认加载都无效,默认加载所有。
2)同上,但是执行此文中主程序。结果如下:
失败:提示在此扩展中没有自适应的方法,进而拒绝创建自适应实例。
3)方法上增加自适应标签@Adaptive
执行主程序,结果如下:
URL中有dog,执行的时候找到的是扩展名为dog的扩展实现。如果改为human呢?应该是hello 加url了。验证确实如此:
如果URL中扩展名为空呢?
失败:提示无name为hello的扩展实现。配置文件中确实没有名为hello的扩展实现。说明对于URL中没有扩展名的自适应,默认使用@SPI中指定的扩展实现。
4)提供默认扩展名为human
执行结果为:
如果无默认扩展名呢?
执行结果为:
失败:提示扩展名为null
5)以上案例均为@Adaptive无参固定,@SPI与URL之间参数变化的场景。此案例@Adaptive设置参数hello.service:
如果URL中无扩展名,执行主程序结果:
说明使用@SPI指定扩展实现。
如果URL中扩展名为dog,执行主程序结果:
说明使用URL中提供扩展名扩展实现。
综合上述@SPI,@Adaptive, URL三者配合使用如下:
URL中提供扩展名:
1)如果@Adaptive无参数,直接加载扩展实现。
2)如果@Adaptive有接口参数,加载URL中符合接口参数的扩展实现;如果无符合接口参数的,加载@SPI中指定扩展实现。
URL中无扩展名信息:无论@Adaptive中是否提供参数,均加载@SPI中指定扩展实现。
对于@Adaptive中参数,此例中为什么是hello.service?这个可以看最开始注释部分其默认参数名规则:
标签:面具 变化 ice png 标准 设置 name 试验 适应
原文地址:https://www.cnblogs.com/ilovebath/p/14869479.html