es").items(Style.QUOTE, onMissingClasses));
}
matchMessage = matchMessage.andCondition(ConditionalOnClass.class, new Object[0]).found("required class", "required classes").items(Style.QUOTE, this.getMatches(onClasses, OnClassCondition.MatchType.PRESENT, classLoader));
}
// 接着找出所有ConditionalOnMissingClass注解的属性
// 它与ConditionalOnClass注解的含义正好相反,所以以下逻辑也与上面相反
onMissingClasses = this.getCandidates(metadata, ConditionalOnMissingClass.class);
if(onMissingClasses != null) {
List present = this.getMatches(onMissingClasses, OnClassCondition.MatchType.PRESENT, classLoader);
if(!present.isEmpty()) {
return ConditionOutcome.noMatch(ConditionMessage.forCondition(ConditionalOnMissingClass.class, new Object[0]).found("unwanted class", "unwanted classes").items(Style.QUOTE, present));
}
matchMessage = matchMessage.andCondition(ConditionalOnMissingClass.class, new Object[0]).didNotFind("unwanted class", "unwanted classes").items(Style.QUOTE, this.getMatches(onMissingClasses, OnClassCondition.MatchType.MISSING, classLoader));
}
return ConditionOutcome.match(matchMessage);
}
// 获得所有annotationType注解的属性
private List<String> getCandidates(AnnotatedTypeMetadata metadata, Class<?> annotationType) {
MultiValueMap attributes = metadata.getAllAnnotationAttributes(annotationType.getName(), true);
ArrayList candidates = new ArrayList();
if(attributes == null) {
return Collections.emptyList();
} else {
this.addAll(candidates, (List)attributes.get("value"));
this.addAll(candidates, (List)attributes.get("name"));
return candidates;
}
}
private void addAll(List<String> list, List<Object> itemsToAdd) {
if(itemsToAdd != null) {
Iterator var3 = itemsToAdd.iterator();
while(var3.hasNext()) {
Object item = var3.next();
Collections.addAll(list, (String[])((String[])item));
}
}
}
// 根据matchType.matches方法来进行匹配
private List<String> getMatches(Collection<String> candidates, OnClassCondition.MatchType matchType, ClassLoader classLoader) {
ArrayList matches = new ArrayList(candidates.size());
Iterator var5 = candidates.iterator();
while(var5.hasNext()) {
String candidate = (String)var5.next();
if(matchType.matches(candidate, classLoader)) {
matches.add(candidate);
}
}
return matches;
}
关于match的具体实现在MatchType中,它是一个枚举类,提供了PRESENT和MISSING两种实现,前者返回类路径中是否存在该类,后者相反。
private static enum MatchType {
PRESENT {
public boolean matches(String className, ClassLoader classLoader) {
return OnClassCondition.MatchType.isPresent(className, classLoader);
}
},
MISSING {
public boolean matches(String className, ClassLoader classLoader) {
return !OnClassCondition.MatchType.isPresent(className, classLoader);
}
};
private MatchType() {
}
// 跟我们之前看过的案例一样,都利用了类加载功能来进行判断
private static boolean isPresent(String className, ClassLoader classLoader) {
if(classLoader == null) {
classLoader = ClassUtils.getDefaultClassLoader();
}
try {
forName(className, classLoader);
return true;
} catch (Throwable var3) {
return false;
}
}
private static Class<?> forName(String className, ClassLoa |