SPI源代码的阅读我们从ServiceConfig.java开始。
ExtensionLoader.java
private ExtensionLoader(Class<?> type) {
this.type = type;
// 用于创建当前type类型扩展类实例的
objectFactory = (type == ExtensionFactory.class ? null : ExtensionLoader.getExtensionLoader(ExtensionFactory.class).getAdaptiveExtension());
}
//判断类上是否有SPI注解
private static <T> boolean withExtensionAnnotation(Class<T> type) {
return type.isAnnotationPresent(SPI.class);
}
@SuppressWarnings("unchecked")
public static <T> ExtensionLoader<T> getExtensionLoader(Class<T> type) {
if (type == null) {
throw new IllegalArgumentException("Extension type == null");
}
if (!type.isInterface()) {
throw new IllegalArgumentException("Extension type (" + type + ") is not an interface!");
}
if (!withExtensionAnnotation(type)) { // 对SPI注解的判断
throw new IllegalArgumentException("Extension type (" + type +
") is not an extension, because it is NOT annotated with @" + SPI.class.getSimpleName() + "!");
}
ExtensionLoader<T> loader = (ExtensionLoader<T>) EXTENSION_LOADERS.get(type);
if (loader == null) {
//如果Map中存在该key,则直接返回该key的value。如果Map中没有该key,那么就添加该key并返回null
EXTENSION_LOADERS.putIfAbsent(type, new ExtensionLoader<T>(type)); // 创建一个loader实例
loader = (ExtensionLoader<T>) EXTENSION_LOADERS.get(type);
}
return loader;
}
objectFactory = (type == ExtensionFactory.class ? null : ExtensionLoader.getExtensionLoader(ExtensionFactory.class).getAdaptiveExtension());
我们这里传入的类型是Protocol.class 类型,所以这里不是null。准备跟踪getExtensionLoader()
public static <T> ExtensionLoader<T> getExtensionLoader(Class<T> type) {
if (type == null) {
throw new IllegalArgumentException("Extension type == null");
}
if (!type.isInterface()) {
throw new IllegalArgumentException("Extension type (" + type + ") is not an interface!");
}
if (!withExtensionAnnotation(type)) { // 对SPI注解的判断
throw new IllegalArgumentException("Extension type (" + type +
") is not an extension, because it is NOT annotated with @" + SPI.class.getSimpleName() + "!");
}
ExtensionLoader<T> loader = (ExtensionLoader<T>) EXTENSION_LOADERS.get(type);
if (loader == null) {
//如果Map中存在该key,则直接返回该key的value。如果Map中没有该key,那么就添加该key并返回null
EXTENSION_LOADERS.putIfAbsent(type, new ExtensionLoader<T>(type)); // 创建一个ExtensionFactory类型的loader实例
loader = (ExtensionLoader<T>) EXTENSION_LOADERS.get(type);
}
return loader;
}
回到ExtensionLoader(Class<?> type)构造方法中跟踪getAdaptiveExtension()
public T getAdaptiveExtension() {
// 从缓存中获取相应实例
Object instance = cachedAdaptiveInstance.get();
// DCL,双重检测锁
if (instance == null) {
if (createAdaptiveInstanceError == null) {
synchronized (cachedAdaptiveInstance) {
instance = cachedAdaptiveInstance.get();
if (instance == null) {
try {
// 创建当前SPI的自适应实例
instance = createAdaptiveExtension();
cachedAdaptiveInstance.set(instance);
} catch (Throwable t) {
createAdaptiveInstanceError = t;
throw new IllegalStateException("Failed to create adaptive instance: " + t.toString(), t);
}
}
}
} else {
throw new IllegalStateException("Failed to create adaptive instance: " + createAdaptiveInstanceError.toString(), createAdaptiveInstanceError);
}
}
return (T) instance;
}
private T createAdaptiveExtension() {
try {
// getAdaptiveExtensionClass() 获取adaptive类,是个class
// newInstance() 调用adaptive类的无参构造器创建一个adpative实例
// injectExtension() 调用实例的setter,完成相关属性实例的注入
return injectExtension((T) getAdaptiveExtensionClass().newInstance());
} catch (Exception e) {
throw new IllegalStateException("Can't create adaptive extension " + type + ", cause: " + e.getMessage(), e);
}
}
private Class<?> getAdaptiveExtensionClass() {
// 用于将当前SPI接口的所有扩展类class缓存起来(四类:普通扩展类、adaptive类、wrapper类,及activate类)
getExtensionClasses();
if (cachedAdaptiveClass != null) {
return cachedAdaptiveClass;
}
// 根据@Adaptive方法,创建adaptive类
return cachedAdaptiveClass = createAdaptiveExtensionClass();
}
private Map<String, Class<?>> getExtensionClasses() {
// cachedClasses 集合中缓存着当前SPI接口的所有直接扩展类(普通扩展类与activate类)
Map<String, Class<?>> classes = cachedClasses.get();
if (classes == null) {
synchronized (cachedClasses) {
classes = cachedClasses.get();
if (classes == null) {
// 加载四类扩展类
classes = loadExtensionClasses();
cachedClasses.set(classes);
}
}
}
// 返回当前SPI接口的所有直接扩展类
return classes;
}
private Map<String, Class<?>> loadExtensionClasses() {
// 缓存SPI接口的默认扩展名
cacheDefaultExtensionName();
// 定义一个map,用于存放直接扩展类
Map<String, Class<?>> extensionClasses = new HashMap<>();
loadDirectory(extensionClasses, DUBBO_INTERNAL_DIRECTORY, type.getName());
// 兼容2.6版本
loadDirectory(extensionClasses, DUBBO_INTERNAL_DIRECTORY, type.getName().replace("org.apache", "com.alibaba"));
loadDirectory(extensionClasses, DUBBO_DIRECTORY, type.getName());
loadDirectory(extensionClasses, DUBBO_DIRECTORY, type.getName().replace("org.apache", "com.alibaba"));
loadDirectory(extensionClasses, SERVICES_DIRECTORY, type.getName());
loadDirectory(extensionClasses, SERVICES_DIRECTORY, type.getName().replace("org.apache", "com.alibaba"));
return extensionClasses;
}
private void cacheDefaultExtensionName() {
// 获取当前SPI接口的SPI注解
final SPI defaultAnnotation = type.getAnnotation(SPI.class);
if (defaultAnnotation != null) {
// 获取SPI注解的value属性值,即默认扩展名
String value = defaultAnnotation.value();
if ((value = value.trim()).length() > 0) {
// 使用逗号分隔value属性值
String[] names = NAME_SEPARATOR.split(value);
if (names.length > 1) {
throw new IllegalStateException("More than 1 default extension name on extension " + type.getName()
+ ": " + Arrays.toString(names));
}
if (names.length == 1) {
cachedDefaultName = names[0];
}
}
}
}
private void loadDirectory(Map<String, Class<?>> extensionClasses, String dir, String type) {
// 拼接出配置文件名
// 例:META-INF/dubbo/internal/org.apache.dubbo.common.extension.ExtensionFactory
String fileName = dir + type;
try {
Enumeration<java.net.URL> urls;
ClassLoader classLoader = findClassLoader();
// 为什么一个文件名会加载出来多个url?
// 因为一个文件名在整个dubbo框架中会存在多个同名文件,每个文件会加载出来一个url
if (classLoader != null) {
urls = classLoader.getResources(fileName);
} else {
urls = ClassLoader.getSystemResources(fileName);
}
if (urls != null) {
while (urls.hasMoreElements()) {
java.net.URL resourceURL = urls.nextElement();
loadResource(extensionClasses, classLoader, resourceURL); // 加载资源
}
}
} catch (Throwable t) {
logger.error("Exception occurred when loading extension class (interface: " +
type + ", description file: " + fileName + ").", t);
}
}
private void loadResource(Map<String, Class<?>> extensionClasses, ClassLoader classLoader, java.net.URL resourceURL) {
try {
// try-with-resource,带资源的try语句,是JDK7的特性
try (BufferedReader reader = new BufferedReader(new InputStreamReader(resourceURL.openStream(), StandardCharsets.UTF_8))) {
String line;
while ((line = reader.readLine()) != null) {
final int ci = line.indexOf('#');
if (ci >= 0) {
line = line.substring(0, ci);
}
line = line.trim();
if (line.length() > 0) {
try {
String name = null;
int i = line.indexOf('=');
if (i > 0) {
name = line.substring(0, i).trim(); // 扩展名
line = line.substring(i + 1).trim(); // 扩展类名
}
if (line.length() > 0) {
// 将指定的类加载并缓存
loadClass(extensionClasses, resourceURL, Class.forName(line, true, classLoader), name);
}
} catch (Throwable t) {
IllegalStateException e = new IllegalStateException("Failed to load extension class (interface: " + type + ", class line: " + line + ") in " + resourceURL + ", cause: " + t.getMessage(), t);
exceptions.put(line, e);
}
}
}
}
} catch (Throwable t) {
logger.error("Exception occurred when loading extension class (interface: " +
type + ", class file: " + resourceURL + ") in " + resourceURL, t);
}
}
private void loadClass(Map<String, Class<?>> extensionClasses, java.net.URL resourceURL, Class<?> clazz, String name) throws NoSuchMethodException {
// 判断当前类是否实现当前的SPI接口了
if (!type.isAssignableFrom(clazz)) {
throw new IllegalStateException("Error occurred when loading extension class (interface: " +
type + ", class line: " + clazz.getName() + "), class "
+ clazz.getName() + " is not subtype of interface.");
}
// 判断当前类是否是adaptive类
if (clazz.isAnnotationPresent(Adaptive.class)) {
// 缓存这个类
cacheAdaptiveClass(clazz);
} else if (isWrapperClass(clazz)) { // 判断当前类是否是wrapper类
// 缓存这个类
cacheWrapperClass(clazz);
} else { // 处理普通扩展类与activate类的情况
// 验证扩展类是否具有无参构造器。
// 若没有,则直接抛出异常,后面的代码就不会执行了。若有,则什么也不做
clazz.getConstructor();
// 处理扩展类为空的情况
if (StringUtils.isEmpty(name)) {
// 找一个扩展名
name = findAnnotationName(clazz);
if (name.length() == 0) {
throw new IllegalStateException("No such extension name for the class " + clazz.getName() + " in the config " + resourceURL);
}
}
// 使用逗号分隔扩展名
String[] names = NAME_SEPARATOR.split(name);
if (ArrayUtils.isNotEmpty(names)) {
// 使用第一个扩展名缓存activate类
cacheActivateClass(clazz, names[0]);
for (String n : names) {
// 缓存第一个name
cacheName(clazz, n);
// 将当前class缓存到一个map
saveInExtensionClass(extensionClasses, clazz, n);
}
}
}
}
private void cacheAdaptiveClass(Class<?> clazz) {
if (cachedAdaptiveClass == null) {
cachedAdaptiveClass = clazz;
// 若缓存中已经存在了adaptive类,且与当前类不同,则抛出异常。因为adaptive类只能有一个
} else if (!cachedAdaptiveClass.equals(clazz)) {
throw new IllegalStateException("More than 1 adaptive class found: "
+ cachedAdaptiveClass.getClass().getName()
+ ", " + clazz.getClass().getName());
}
}
private void cacheWrapperClass(Class<?> clazz) {
if (cachedWrapperClasses == null) {
cachedWrapperClasses = new ConcurrentHashSet<>();
}
// 将这个类写入到缓存set
cachedWrapperClasses.add(clazz);
}
private void cacheName(Class<?> clazz, String name) {
// 使用这个class缓存第一个name
if (!cachedNames.containsKey(clazz)) {
cachedNames.put(clazz, name);
}
}
private void saveInExtensionClass(Map<String, Class<?>> extensionClasses, Class<?> clazz, String name) {
Class<?> c = extensionClasses.get(name);
if (c == null) {
// 每一个扩展名都会与class配对写入到map中
extensionClasses.put(name, clazz);
} else if (c != clazz) {
throw new IllegalStateException("Duplicate extension " + type.getName() + " name " + name + " on " + c.getName() + " and " + clazz.getName());
}
}
缓存类的源码阅读完了,接下来返回到 private Class<?> getAdaptiveExtensionClass() 中 createAdaptiveExtensionClass() 的adaptive类创建的过程
private Class<?> createAdaptiveExtensionClass() {
// 生成adaptive类代码
String code = new AdaptiveClassCodeGenerator(type, cachedDefaultName).generate();
ClassLoader classLoader = findClassLoader();
// 获取到Compiler类型的adaptive类实例
org.apache.dubbo.common.compiler.Compiler compiler = ExtensionLoader
.getExtensionLoader(org.apache.dubbo.common.compiler.Compiler.class)
.getAdaptiveExtension();
// 调用adaptiveCompiler的compile()
return compiler.compile(code, classLoader);
}
AdaptiveClassCodeGenerator.java
public String generate() {
// no need to generate adaptive class since there's no adaptive method found.
// 若当前SPI接口中不包含@Adaptive方法,则抛出异常
if (!hasAdaptiveMethod()) {
throw new IllegalStateException("No adaptive method exist on extension " + type.getName() + ", refuse to create the adaptive class!");
}
// 通过字符串拼接方式,生成代码
StringBuilder code = new StringBuilder();
code.append(generatePackageInfo()); //生成包信息代码
code.append(generateImports()); //生成需要导入的包路径代码
code.append(generateClassDeclaration());//生成类名称和头部信息
Method[] methods = type.getMethods();
for (Method method : methods) {
code.append(generateMethod(method)); //生生该类中的方法
}
code.append("}");
if (logger.isDebugEnabled()) {
logger.debug(code.toString());
}
return code.toString();
}
返回到ExtensionLoader.java 跟踪createAdaptiveExtensionClass() 中的 compile() 动态编译方法
private static volatile String DEFAULT_COMPILER;
public static void setDefaultCompiler(String compiler) {
DEFAULT_COMPILER = compiler;
}
@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 {
// 获取默认扩展名的实例,即javassistCompiler的实例
compiler = loader.getDefaultExtension();
}
// 调用javassistCompiler的compile()
return compiler.compile(code, classLoader);
}
}
ExtensionLoader.java
// 获取指定名称的扩展类实例
public T getExtension(String name) {
if (StringUtils.isEmpty(name)) {
throw new IllegalArgumentException("Extension name == null");
}
if ("true".equals(name)) {
return getDefaultExtension();
}
// 从我们刚才跟踪过的这个熟系的缓存里面根据指定名称 来获取实例
final Holder<Object> holder = getOrCreateHolder(name);
Object instance = holder.get();
if (instance == null) {
synchronized (holder) {
instance = holder.get();
if (instance == null) {
// 创建指定名称的扩展类实例
instance = createExtension(name);
holder.set(instance);
}
}
}
return (T) instance;
}
private T createExtension(String name) {
// getExtensionClasses() 返回当前SPI接口的所有直接扩展类,是个map
// 其key为扩展名,value为直接扩展类的class
Class<?> clazz = getExtensionClasses().get(name);
if (clazz == null) {
throw findException(name);
}
try {
// 从缓存中获取指定类对应的实例,若为null,则创建一个实例
T instance = (T) EXTENSION_INSTANCES.get(clazz);
if (instance == null) {
EXTENSION_INSTANCES.putIfAbsent(clazz, clazz.newInstance());
instance = (T) EXTENSION_INSTANCES.get(clazz);
}
// 调用instance实例的setter完成注入
injectExtension(instance);
// 获取当前SPI接口类型的所有wrapper类
Set<Class<?>> wrapperClasses = cachedWrapperClasses;
// 遍历所有wrapper,逐层对instance实例进行包装
if (CollectionUtils.isNotEmpty(wrapperClasses)) {
for (Class<?> wrapperClass : wrapperClasses) {
instance = injectExtension((T) wrapperClass.getConstructor(type).newInstance(instance));
}
}
// 返回的是包装过的instance
return instance;
} catch (Throwable t) {
throw new IllegalStateException("Extension instance (name: " + name + ", class: " +
type + ") couldn't be instantiated: " + t.getMessage(), t);
}
}
private T createExtension(String name) {
// getExtensionClasses() 返回当前SPI接口的所有直接扩展类,是个map
// 其key为扩展名,value为直接扩展类的class
Class<?> clazz = getExtensionClasses().get(name);
if (clazz == null) {
throw findException(name);
}
try {
// 从缓存中获取指定类对应的实例,若为null,则创建一个实例
T instance = (T) EXTENSION_INSTANCES.get(clazz);
if (instance == null) {
EXTENSION_INSTANCES.putIfAbsent(clazz, clazz.newInstance());
instance = (T) EXTENSION_INSTANCES.get(clazz);
}
// 调用instance实例的setter完成注入
injectExtension(instance);
// 获取当前SPI接口类型的所有wrapper类
Set<Class<?>> wrapperClasses = cachedWrapperClasses;
// 遍历所有wrapper,逐层对instance实例进行包装
if (CollectionUtils.isNotEmpty(wrapperClasses)) {
for (Class<?> wrapperClass : wrapperClasses) {
//看 这里就是我们之前说的构造方法中传入了SPI接口的有参构造函数作为注入
// 对该SPI接口进行实例化,用于调用SPI接口中的方法时进行方法增强
instance = injectExtension((T) wrapperClass.getConstructor(type).newInstance(instance));
}
}
// 返回的是包装过的instance
return instance;
} catch (Throwable t) {
throw new IllegalStateException("Extension instance (name: " + name + ", class: " +
type + ") couldn't be instantiated: " + t.getMessage(), t);
}
}
private T injectExtension(T instance) {
try {
if (objectFactory != null) {
// 遍历当前instance中的所有方法
for (Method method : instance.getClass().getMethods()) {
// 仅对setter方法进行处理
if (isSetter(method)) {
/**
* Check {@link DisableInject} to see if we need auto injection for this property
*/
// 若一个setter方法上有@DisableInject注解,则不进行注入
if (method.getAnnotation(DisableInject.class) != null) {
continue;
}
// 获取当前setter方法的参数类型
Class<?> pt = method.getParameterTypes()[0];
// 若setter方法的参数类型为基本数据类型,则不进行注入
if (ReflectUtils.isPrimitives(pt)) {
continue;
}
try {
// 获取setter方法的形参名称
String property = getSetterProperty(method);
// 获取要注入的实例,即setter的实参
Object object = objectFactory.getExtension(pt, property);
if (object != null) {
// 调用setter完成注入
method.invoke(instance, object);
}
} catch (Exception e) {
logger.error("Failed to inject via method " + method.getName()
+ " of interface " + type.getName() + ": " + e.getMessage(), e);
}
}
}
}
} catch (Exception e) {
logger.error(e.getMessage(), e);
}
return instance;
}
回到 AdaptiveCompiler.java 中的 compile() 方法中来跟踪一下 javassistCompiler 的实现
AbstractCompiler.java
/**
*
* @param code 生成好的代码字符串
* @param classLoader 加载code的类加载器
* @return
*/
@Override
public Class<?> compile(String code, ClassLoader classLoader) {
code = code.trim();
// 从code中将package信息摘出
Matcher matcher = PACKAGE_PATTERN.matcher(code);
String pkg;
if (matcher.find()) {
pkg = matcher.group(1);
} else {
pkg = "";
}
// 从code中将class信息摘出
matcher = CLASS_PATTERN.matcher(code);
String cls;
if (matcher.find()) {
cls = matcher.group(1);
} else {
throw new IllegalArgumentException("No such class name in " + code);
}
// 拼接出要加载的全限定性类名
String className = pkg != null && pkg.length() > 0 ? pkg + "." + cls : cls;
try {
// 加载名称为className的类
return Class.forName(className, true, org.apache.dubbo.common.utils.ClassUtils.getCallerClassLoader(getClass()));
} catch (ClassNotFoundException e) {
if (!code.endsWith("}")) {
throw new IllegalStateException("The java code not endsWith \"}\", code: \n" + code + "\n");
}
try { // 调用JavassistCompiler的doCompile(),对code使用javassist技术进行动态编译
return doCompile(className, code);
} catch (RuntimeException t) {
throw t;
} catch (Throwable t) {
throw new IllegalStateException("Failed to compile class, cause: " + t.getMessage() + ", class: " + className + ", code: \n" + code + "\n, stack: " + ClassUtils.toString(t));
}
}
}
JavassistCompiler.java
/**
* JavassistCompiler. (SPI, Singleton, ThreadSafe)
*/
public class JavassistCompiler extends AbstractCompiler {
private static final Pattern IMPORT_PATTERN = Pattern.compile("import\\s+([\\w\\.\\*]+);\n");
private static final Pattern EXTENDS_PATTERN = Pattern.compile("\\s+extends\\s+([\\w\\.]+)[^\\{]*\\{\n");
private static final Pattern IMPLEMENTS_PATTERN = Pattern.compile("\\s+implements\\s+([\\w\\.]+)\\s*\\{\n");
private static final Pattern METHODS_PATTERN = Pattern.compile("\n(private|public|protected)\\s+");
private static final Pattern FIELD_PATTERN = Pattern.compile("[^\n]+=[^\n]+;");
@Override
public Class<?> doCompile(String name, String source) throws Throwable {
// 创建一个Builder
CtClassBuilder builder = new CtClassBuilder();
// 下面的代码都是对builder实例的各种初始化
builder.setClassName(name);
// process imported classes
Matcher matcher = IMPORT_PATTERN.matcher(source);
while (matcher.find()) {
builder.addImports(matcher.group(1).trim());
}
// process extended super class
matcher = EXTENDS_PATTERN.matcher(source);
if (matcher.find()) {
builder.setSuperClassName(matcher.group(1).trim());
}
// process implemented interfaces
matcher = IMPLEMENTS_PATTERN.matcher(source);
if (matcher.find()) {
String[] ifaces = matcher.group(1).trim().split("\\,");
Arrays.stream(ifaces).forEach(i -> builder.addInterface(i.trim()));
}
// process constructors, fields, methods
String body = source.substring(source.indexOf('{') + 1, source.length() - 1);
String[] methods = METHODS_PATTERN.split(body);
String className = ClassUtils.getSimpleClassName(name);
Arrays.stream(methods).map(String::trim).filter(m -> !m.isEmpty()).forEach(method -> {
if (method.startsWith(className)) {
builder.addConstructor("public " + method);
} else if (FIELD_PATTERN.matcher(method).matches()) {
builder.addField("private " + method);
} else {
builder.addMethod("public " + method);
}
});
// compile
ClassLoader classLoader = org.apache.dubbo.common.utils.ClassUtils.getCallerClassLoader(getClass());
// 使用builder构建出一个CtClass
CtClass cls = builder.build(classLoader);
// 使用CtClass获取到一个class
return cls.toClass(classLoader, JavassistCompiler.class.getProtectionDomain());
}
}
接下来跟踪一下JDK的动态编译源代码
public Class<?> doCompile(String name, String sourceCode) throws Throwable {
int i = name.lastIndexOf('.');
String packageName = i < 0 ? "" : name.substring(0, i);
String className = i < 0 ? name : name.substring(i + 1);
// 字符串代码会被包装成一个文件对象
JavaFileObjectImpl javaFileObject = new JavaFileObjectImpl(className, sourceCode);
// javaFileManager接口。主要管理文件的读取和输出位置。
// 因为实现类ForwardingDavaFileManager构造器是protect类型 所以Dubbo扩展了自己的 JavaFileManagerImpl
javaFileManager.putFileForInput(StandardLocation.SOURCE_PATH, packageName,
className + ClassUtils.JAVA_EXTENSION, javaFileObject);
//生成具体的对象类
Boolean result = compiler.getTask(null, javaFileManager, diagnosticCollector, options,
null, Arrays.asList(javaFileObject)).call();
if (result == null || !result) {
throw new IllegalStateException("Compilation failed. class: " + name + ", diagnostics: " + diagnosticCollector);
}
// 使用自定义的 ClassLoaderImpl 完成资源的加载
return classLoader.loadClass(name);
}