getAdaptiveExtension() 方法,获得自适应拓展对象:
/**
* 缓存的自适应( Adaptive )拓展对象
*/
private final Holder<Object> cachedAdaptiveInstance = new Holder<Object>();
/**
* 创建 {@link #cachedAdaptiveInstance} 时发生的异常。
*
* 发生异常后,不再创建,参见 {@link #createAdaptiveExtension()}
*/
private volatile Throwable createAdaptiveInstanceError;
/**
* 获得自适应拓展对象
*
* @return 拓展对象
*/
@SuppressWarnings("unchecked")
public T getAdaptiveExtension() {
// 从缓存中,获得自适应拓展对象
Object instance = cachedAdaptiveInstance.get();
if (instance == null) {
// 若之前未创建报错,
if (createAdaptiveInstanceError == null) {
synchronized (cachedAdaptiveInstance) {
instance = cachedAdaptiveInstance.get();
if (instance == null) {
try {
// 创建自适应拓展对象
instance = createAdaptiveExtension();
// 设置到缓存
cachedAdaptiveInstance.set(instance);
} catch (Throwable t) {
// 记录异常
createAdaptiveInstanceError = t;
throw new IllegalStateException("fail to create adaptive instance: " + t.toString(), t);
}
}
}
// 若之前创建报错,则抛出异常 IllegalStateException
} else {
throw new IllegalStateException("fail to create adaptive instance: " + createAdaptiveInstanceError.toString(), createAdaptiveInstanceError);
}
}
return (T) instance;
}
createAdaptiveExtension() 方法,创建自适应拓展对象:
/**
* 创建自适应拓展对象
*
* @return 拓展对象
*/
@SuppressWarnings("unchecked")
private T createAdaptiveExtension() {
try {
return injectExtension((T) getAdaptiveExtensionClass().newInstance());
} catch (Exception e) {
throw new IllegalStateException("Can not create adaptive extension " + type + ", cause: " + e.getMessage(), e);
}
}
getAdaptiveExtensionClass() 方法,获得自适应拓展类:
/**
* @return 自适应拓展类
*/
private Class<?> getAdaptiveExtensionClass() {
getExtensionClasses();
if (cachedAdaptiveClass != null) {
return cachedAdaptiveClass;
}
return cachedAdaptiveClass = createAdaptiveExtensionClass();
}
createAdaptiveExtensionClassCode() 方法,自动生成自适应拓展的代码实现,并编译后返回该类:
/**
* 自动生成自适应拓展的代码实现,并编译后返回该类。
*
* @return 类
*/
private Class<?> createAdaptiveExtensionClass() {
// 自动生成自适应拓展的代码实现的字符串
String code = createAdaptiveExtensionClassCode();
// 编译代码,并返回该类
ClassLoader classLoader = findClassLoader();
com.alibaba.dubbo.common.compiler.Compiler compiler = ExtensionLoader.getExtensionLoader(com.alibaba.dubbo.common.compiler.Compiler.class).getAdaptiveExtension();
return compiler.compile(code, classLoader);
}
getExtensionLoader(url, key, group) 方法,获得符合自动激活条件的拓展对象数组:
/**
* This is equivalent to {@code getActivateExtension(url, url.getParameter(key).split(","), null)}
*
* 获得符合自动激活条件的拓展对象数组
*
* @param url url
* @param key url parameter key which used to get extension point names
* Dubbo URL 参数名
* @param group group
* 过滤分组名
* @return extension list which are activated.
* @see #getActivateExtension(com.alibaba.dubbo.common.URL, String[], String)
*/
public List<T> getActivateExtension(URL url, String key, String group) {
// 从 Dubbo URL 获得参数值
String value = url.getParameter(key);
// 获得符合自动激活条件的拓展对象数组
return getActivateExtension(url, value == null || value.length() == 0 ? null : Constants.COMMA_SPLIT_PATTERN.split(value), group);
}
/**
* Get activate extensions.
*
* 获得符合自动激活条件的拓展对象数组
*
* @param url url
* @param values extension point names
* @param group group
* @return extension list which are activated
* @see com.alibaba.dubbo.common.extension.Activate
*/
public List<T> getActivateExtension(URL url, String[] values, String group) {
List<T> exts = new ArrayList<T>();
List<String> names = values == null ? new ArrayList<String>(0) : Arrays.asList(values);
// 处理自动激活的拓展对象们
// 判断不存在配置 `"-name"` 。例如,<dubbo:service filter="-default" /> ,代表移除所有默认过滤器。
if (!names.contains(Constants.REMOVE_VALUE_PREFIX + Constants.DEFAULT_KEY)) {
// 获得拓展实现类数组
getExtensionClasses();
// 循环
for (Map.Entry<String, Activate> entry : cachedActivates.entrySet()) {
String name = entry.getKey();
Activate activate = entry.getValue();
if (isMatchGroup(group, activate.group())) { // 匹配分组
// 获得拓展对象
T ext = getExtension(name);
if (!names.contains(name) // 不包含在自定义配置里。如果包含,会在下面的代码处理。
&& !names.contains(Constants.REMOVE_VALUE_PREFIX + name) // 判断是否配置移除。例如 <dubbo:service filter="-monitor" />,则 MonitorFilter 会被移除
&& isActive(activate, url)) { // 判断是否激活
exts.add(ext);
}
}
}
// 排序
Collections.sort(exts, ActivateComparator.COMPARATOR);
}
// 处理自定义配置的拓展对象们。例如在 <dubbo:service filter="demo" /> ,代表需要加入 DemoFilter (这个是笔者自定义的)。
List<T> usrs = new ArrayList<T>();
for (int i = 0; i < names.size(); i++) {
String name = names.get(i);
if (!name.startsWith(Constants.REMOVE_VALUE_PREFIX) && !names.contains(Constants.REMOVE_VALUE_PREFIX + name)) { // 判断非移除的
// 将配置的自定义在自动激活的拓展对象们前面。例如,<dubbo:service filter="demo,default,demo2" /> ,则 DemoFilter 就会放在默认的过滤器前面。
if (Constants.DEFAULT_KEY.equals(name)) {
if (!usrs.isEmpty()) {
exts.addAll(0, usrs);
usrs.clear();
}
} else {
// 获得拓展对象
T ext = getExtension(name);
usrs.add(ext);
}
}
}
// 添加到结果集
if (!usrs.isEmpty()) {
exts.addAll(usrs);
}
return exts;
}
com.alibaba.dubbo.common.extension.@SPI ,扩展点接口的标识(value ,默认拓展实现类的名字。):
@Documented
@Retention(RetentionPolicy.RUNTIME)
@Target({ElementType.TYPE})
public @interface SPI {
/**
* default extension name
*/
String value() default "";
}
@Adaptive ,自适应拓展信息的标记:
@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
*/
/**
* 从 {@link URL }的 Key 名,对应的 Value 作为要 Adapt 成的 Extension 名。
* <p>
* 如果 {@link URL} 这些 Key 都没有 Value ,使用 缺省的扩展(在接口的{@link SPI}中设定的值)。<br>
* 比如,<code>String[] {"key1", "key2"}</code>,表示
* <ol>
* <li>先在URL上找key1的Value作为要Adapt成的Extension名;
* <li>key1没有Value,则使用key2的Value作为要Adapt成的Extension名。
* <li>key2没有Value,使用缺省的扩展。
* <li>如果没有设定缺省扩展,则方法调用会抛出{@link IllegalStateException}。
* </ol>
* <p>
* 如果不设置则缺省使用Extension接口类名的点分隔小写字串。<br>
* 即对于Extension接口 {@code com.alibaba.dubbo.xxx.YyyInvokerWrapper} 的缺省值为 <code>String[] {"yyy.invoker.wrapper"}</code>
*
* @see SPI#value()
*/
String[] value() default {};
}
@Adaptive 注解,添加在类和方法上,两种不同的使用方式不同:
- 记在类上,代表手动实现它是一个拓展接口的 Adaptive 拓展实现类。
- 标记在拓展接口的方法上,代表自动生成代码实现该接口的 Adaptive 拓展实现类。
@Activate ,自动激活条件的标记:
@Documented
@Retention(RetentionPolicy.RUNTIME)
@Target({ElementType.TYPE, ElementType.METHOD})
public @interface Activate {
/**
* Activate the current extension when one of the groups matches. The group passed into
* {@link ExtensionLoader#getActivateExtension(URL, String, String)} will be used for matching.
*
* @return group names to match
* @see ExtensionLoader#getActivateExtension(URL, String, String)
*/
/**
* Group过滤条件。
* <br />
* 包含{@link ExtensionLoader#getActivateExtension}的group参数给的值,则返回扩展。
* <br />
* 如没有Group设置,则不过滤。
*/
String[] group() default {};
/**
* Activate the current extension when the specified keys appear in the URL's parameters.
* <p>
* For example, given <code>@Activate("cache, validation")</code>, the current extension will be return only when
* there's either <code>cache</code> or <code>validation</code> key appeared in the URL's parameters.
* </p>
*
* @return URL parameter keys
* @see ExtensionLoader#getActivateExtension(URL, String)
* @see ExtensionLoader#getActivateExtension(URL, String, String)
*/
/**
* Key过滤条件。包含{@link ExtensionLoader#getActivateExtension}的URL的参数Key中有,则返回扩展。
* <p/>
* 示例:<br/>
* 注解的值 <code>@Activate("cache,validatioin")</code>,
* 则{@link ExtensionLoader#getActivateExtension}的URL的参数有<code>cache</code>Key,或是<code>validatioin</code>则返回扩展。
* <br/>
* 如没有设置,则不过滤。
*/
String[] value() default {};
/**
* Relative ordering info, optional
*
* @return extension list which should be put before the current one
*/
/**
* 排序信息,可以不提供。
*/
String[] before() default {};
/**
* Relative ordering info, optional
*
* @return extension list which should be put after the current one
*/
/**
* 排序信息,可以不提供。
*/
String[] after() default {};
/**
* Absolute ordering info, optional
*
* @return absolute ordering info
*/
/**
* 排序信息,可以不提供。
*/
int order() default 0;
}
ExtensionFactory ,拓展工厂接口(ExtensionFactory 自身也是拓展接口,基于 Dubbo SPI 加载具体拓展实现类):
/**
* ExtensionFactory
*
* 拓展工厂接口
*/
@SPI
public interface ExtensionFactory {
/**
* Get extension.
*
* 获得拓展对象
*
* @param type object type. 拓展接口
* @param name object name. 拓展名
* @return object instance. 拓展对象
*/
<T> T getExtension(Class<T> type, String name);
}
AdaptiveExtensionFactory自适应 ExtensionFactory 拓展实现类:
@Adaptive
public class AdaptiveExtensionFactory implements ExtensionFactory {
/**
* ExtensionFactory 拓展对象集合
*/
private final List<ExtensionFactory> factories;
public AdaptiveExtensionFactory() {
// 使用 ExtensionLoader 加载拓展对象实现类。
ExtensionLoader<ExtensionFactory> loader = ExtensionLoader.getExtensionLoader(ExtensionFactory.class);
List<ExtensionFactory> list = new ArrayList<ExtensionFactory>();
for (String name : loader.getSupportedExtensions()) {
list.add(loader.getExtension(name));
}
factories = Collections.unmodifiableList(list);
}
public <T> T getExtension(Class<T> type, String name) {
// 遍历工厂数组,直到获得到属性
for (ExtensionFactory factory : factories) {
T extension = factory.getExtension(type, name);
if (extension != null) {
return extension;
}
}
return null;
}
}
SpiExtensionFactory,SPI ExtensionFactory 拓展实现类:
public class SpiExtensionFactory implements ExtensionFactory {
/**
* 获得拓展对象
*
* @param type object type. 拓展接口
* @param name object name. 拓展名
* @param <T> 泛型
* @return 拓展对象
*/
public <T> T getExtension(Class<T> type, String name) {
if (type.isInterface() && type.isAnnotationPresent(SPI.class)) { // 校验是 @SPI
// 加载拓展接口对应的 ExtensionLoader 对象
ExtensionLoader<T> loader = ExtensionLoader.getExtensionLoader(type);
// 加载拓展对象
if (!loader.getSupportedExtensions().isEmpty()) {
return loader.getAdaptiveExtension();
}
}
return null;
}
}
SpringExtensionFactory, Spring ExtensionFactory 拓展实现类:
public class SpringExtensionFactory implements ExtensionFactory {
/**
* Spring Context 集合
*/
private static final Set<ApplicationContext> contexts = new ConcurrentHashSet<ApplicationContext>();
public static void addApplicationContext(ApplicationContext context) {
contexts.add(context);
}
public static void removeApplicationContext(ApplicationContext context) {
contexts.remove(context);
}
@Override
@SuppressWarnings("unchecked")
//getExtension(type, name) 方法,遍历 contexts ,调用其 ApplicationContext的getBean(name) 方法,获得 Bean 对象,直到成功并且值类型正确。
public <T> T getExtension(Class<T> type, String name) {
for (ApplicationContext context : contexts) {
if (context.containsBean(name)) {
// 获得属性
Object bean = context.getBean(name);
// 判断类型
if (type.isInstance(bean)) {
return (T) bean;
}
}
}
return null;
}
}