@SuppressWarnings("unchecked")publicstatic<T> ExtensionLoader<T>getExtensionLoader(Class<T> type){if(type == null){thrownewIllegalArgumentException("Extension type == null");}if(!type.isInterface()){thrownewIllegalArgumentException("Extension type ("+ type +") is not an interface!");}// 接口上需要标识@SPI注解if(!withExtensionAnnotation(type)){thrownewIllegalArgumentException("Extension type ("+ type +") is not an extension, because it is NOT annotated with @"+ SPI.class.getSimpleName()+"!");}// 从缓存中查找,没有就新建一个,放入到缓存map中
ExtensionLoader<T> loader =(ExtensionLoader<T>) EXTENSION_LOADERS.get(type);if(loader == null){// putIfAbsent,保证了线程安全性
EXTENSION_LOADERS.putIfAbsent(type,newExtensionLoader<T>(type));
loader =(ExtensionLoader<T>) EXTENSION_LOADERS.get(type);}return loader;}
privatevoidloadClass(Map<String, Class<?>> extensionClasses, java.net.URL resourceURL, Class<?> clazz, String name,boolean overridden)throws NoSuchMethodException {// 如果已加载的类不是该接口的子类, 则抛出异常if(!type.isAssignableFrom(clazz)){thrownewIllegalStateException("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)){// 设置 cachedAdaptiveClass缓存,注意这里只允许实现类只有一个类上有Adaptive注解,否则会抛出异常cacheAdaptiveClass(clazz, overridden);// 检测clazz是否是Wrapper类型(含有单个该类型参数的构造方法,即为包装类型),如果是,就添加到cachedWrapperClasses集合中}elseif(isWrapperClass(clazz)){cacheWrapperClass(clazz);}else{// 检测 clazz 是否有默认的构造方法,如果没有,则抛出异常
clazz.getConstructor();if(StringUtils.isEmpty(name)){// 没有配置name,则按照注解Extension(已废弃),类名等方式重新获取到name
name =findAnnotationName(clazz);if(name.length()==0){thrownewIllegalStateException("No such extension name for the class "+ clazz.getName()+" in the config "+ resourceURL);}}// 切分name
String[] names = NAME_SEPARATOR.split(name);if(ArrayUtils.isNotEmpty(names)){// 取第一个名称,缓存到cachedActivates中(name到Activate的映射)cacheActivateClass(clazz, names[0]);for(String n : names){// 缓存Class到name的映射cacheName(clazz, n);// 保存name到Class的映射saveInExtensionClass(extensionClasses, clazz, n, overridden);}}}}/**
* put clazz in extensionClasses
*/privatevoidsaveInExtensionClass(Map<String, Class<?>> extensionClasses, Class<?> clazz, String name,boolean overridden){
Class<?> c = extensionClasses.get(name);if(c == null || overridden){// 保存name到Clazz的映射关系
extensionClasses.put(name, clazz);}elseif(c != clazz){// 如果同一个name对应不同的Class,则抛出异常
String duplicateMsg ="Duplicate extension "+ type.getName()+" name "+ name +" on "+ c.getName()+" and "+ clazz.getName();
logger.error(duplicateMsg);thrownewIllegalStateException(duplicateMsg);}}