@Adaptive可以标记在类、接口、枚举和方法上,但是整个Dubbo中只有几个地方使用在类级别上,如AdaptiveExtensionFactory 和AdaptiveCompiler,其余都标注在方法上。如果标记在接口的方法上,即方法级别的注解,则可以通过参数动态的获得实现类,怎么动态的获取需要看getExtension方法。在后面我会说到这里
/**
* Provide helpful information for {@link ExtensionLoader} to inject dependency extension instance.
*
* @see ExtensionLoader
* @see URL
*/
@Documented
@Retention(RetentionPolicy.RUNTIME)
@Target({ElementType.TYPE, ElementType.METHOD})
public @interface Adaptive {
/**
* Decide which target extension to be injected. The name of the target extension is decided by the parameter passed
* in the URL, and the parameter names are given by this method.
* <p>
* If the specified parameters are not found from {@link URL}, then the default extension will be used for
* dependency injection (specified in its interface's {@link SPI}).
* <p>
* For examples, given <code>String[] {"key1", "key2"}</code>:
* <ol>
* <li>find parameter 'key1' in URL, use its value as the extension's name</li>
* <li>try 'key2' for extension's name if 'key1' is not found (or its value is empty) in URL</li>
* <li>use default extension if 'key2' doesn't appear either</li>
* <li>otherwise, throw {@link IllegalStateException}</li>
* </ol>
* If default extension's name is not give on interface's {@link SPI}, then a name is generated from interface's
* class name with the rule: divide classname from capital char into several parts, and separate the parts with
* dot '.', for example: for {@code com.alibaba.dubbo.xxx.YyyInvokerWrapper}, its default name is
* <code>String[] {"yyy.invoker.wrapper"}</code>. This name will be used to search for parameter from URL.
*
* @return parameter key names in URL
*/
String[] value() default {};
}
我们先看下Dubbo中标注在类上的两个类AdaptiveExtensionFactory和AdaptiveCompiler
1.AdaptiveExtensionFactory:自适应的扩展工厂类,这个类里面一个构造方法,一个获取扩展的方法,构造方法就是获取到所有的扩展工厂并且组装到一个集合当中,getExtension方法就是根据类型以及名称来获取ExtensionFactory
/**
* AdaptiveExtensionFactory
*/
@Adaptive
public class AdaptiveExtensionFactory implements ExtensionFactory {
private final List<ExtensionFactory> factories;
public AdaptiveExtensionFactory() {
// 获取ExtensionFactory的类加载器
ExtensionLoader<ExtensionFactory> loader = ExtensionLoader.getExtensionLoader(ExtensionFactory.class);
List<ExtensionFactory> list = new ArrayList<ExtensionFactory>();
/*
获取所有ExtensionFactory的需要加载的实现类、
加载下面三个目录下的扩展类
1.META-INF/dubbo/internal/
2.META-INF/dubbo/
3.META-INF/services/
*/
for (String name : loader.getSupportedExtensions()) {
list.add(loader.getExtension(name));
}
factories = Collections.unmodifiableList(list);
}
@Override
public <T> T getExtension(Class<T> type, String name) {
for (ExtensionFactory factory : factories) {
// 根据类型和名称,返回ExtensionFactory
T extension = factory.getExtension(type, name);
if (extension != null) {
return extension;
}
}
return null;
}
}
2.AdaptiveCompiler,选择合适的编译器编译代码
@Adaptive
public class AdaptiveCompiler implements Compiler {
private static volatile String DEFAULT_COMPILER;
public static void setDefaultCompiler(String compiler) {
DEFAULT_COMPILER = compiler;
}
/**
* 编译代码
* @param code Java source code 要编译的代码
* @param classLoader classloader 类加载器
* @return class文件
*/
@Override
public Class<?> compile(String code, ClassLoader classLoader) {
Compiler compiler;
// 获取类编译器
ExtensionLoader<Compiler> loader = ExtensionLoader.getExtensionLoader(Compiler.class);
String name = DEFAULT_COMPILER; // copy reference
// 选择编译器
if (name != null && name.length() > 0) {
compiler = loader.getExtension(name);
} else {
compiler = loader.getDefaultExtension();
}
// 编译代码
return compiler.compile(code, classLoader);
}
}
假如@Adaptive注解加在方法上,就是方法级别的适应
未完待续