在 spring 注解模式下,不管是采用 @Autowired 注入 bean,或者是采用 @Value 为 bean 中指定的 Field 注入值,亦或者在 @Bean 修饰的方法中携带参数,都会涉及到对依赖的 bean 或 值的解析。下面我们来看下,在 spring 中,对依赖的解析到底是怎么实现的。
resolveDependency
// DefaultListableBeanFactory
@Override
@Nullable
public Object resolveDependency(DependencyDescriptor descriptor, @Nullable String requestingBeanName,
@Nullable Set<String> autowiredBeanNames, @Nullable TypeConverter typeConverter) throws BeansException {
// DefaultParameterNameDiscoverer
descriptor.initParameterNameDiscovery(getParameterNameDiscoverer());
if (Optional.class == descriptor.getDependencyType()) {
return createOptionalDependency(descriptor, requestingBeanName);
}
else if (ObjectFactory.class == descriptor.getDependencyType() ||
ObjectProvider.class == descriptor.getDependencyType()) {
return new DependencyObjectProvider(descriptor, requestingBeanName);
}
else if (javaxInjectProviderClass == descriptor.getDependencyType()) {
return new Jsr330Factory().createDependencyProvider(descriptor, requestingBeanName);
}
else {
// ContextAnnotationAutowireCandidateResolver
// AnnotationConfigUtils#registerAnnotationConfigProcessors 时设置
// 判断是否持有 @Lazy 注解
Object result = getAutowireCandidateResolver().getLazyResolutionProxyIfNecessary(
descriptor, requestingBeanName);
if (result == null) {
result = doResolveDependency(descriptor, requestingBeanName, autowiredBeanNames, typeConverter);
}
return result;
}
}
这里先来看看这个 DependencyDescriptor,依赖的描述,继承 InjectionPoint,是一个注入点。从构造方法可知,可作为注入点的共有两个,一个是 MethodParameter,表示方法注入,即 @Bean 修饰方法携带参数,或者 setter 方法上存在 @Value;另一个是 Field,即类中字段注入。不管是哪一种,最后都会封装成一个 DependencyDescriptor。
此处一般不持有 @Lazy 注解,所以调用 doResolveDependency 方法。
@Nullable
public Object doResolveDependency(DependencyDescriptor descriptor, @Nullable String beanName,
@Nullable Set<String> autowiredBeanNames, @Nullable TypeConverter typeConverter) throws BeansException {
InjectionPoint previousInjectionPoint = ConstructorResolver.setCurrentInjectionPoint(descriptor);
try {
Object shortcut = descriptor.resolveShortcut(this);
if (shortcut != null) {
return shortcut;
}
// 获取依赖的类型
// MethodParameter 为 @Bean 方法返回值类型
Class<?> type = descriptor.getDependencyType();
// ContextAnnotationAutowireCandidateResolver
// 如果 @Value 中存在占位符 ${},此时解析返回的 value 中包含 ${}
// 方法上只定义 @Bean,此时不持有 @Value,返回 null
Object value = getAutowireCandidateResolver().getSuggestedValue(descriptor);
if (value != null) {
// @Value String 类型,利用之前注册的 embeddedValueResolvers 进行解析
if (value instanceof String) {
// 占位符处理,得到真正的值
String strVal = resolveEmbeddedValue((String) value);
BeanDefinition bd = (beanName != null && containsBean(beanName) ?
getMergedBeanDefinition(beanName) : null);
// SpEl spring EL 表达处理
value = evaluateBeanDefinitionString(strVal, bd);
}
TypeConverter converter = (typeConverter != null ? typeConverter : getTypeConverter());
try {
// 类型转换后直接返回
return converter.convertIfNecessary(value, type, descriptor.getTypeDescriptor());
}
catch (UnsupportedOperationException ex) {
// 自定义 TypeConverter 不支持 TypeDescriptor 时的解决方法
return (descriptor.getField() != null ?
converter.convertIfNecessary(value, type, descriptor.getField()) :
converter.convertIfNecessary(value, type, descriptor.getMethodParameter()));
}
}
// 注入点类型为复合类型的处理
Object multipleBeans = resolveMultipleBeans(descriptor, beanName, autowiredBeanNames, typeConverter);
if (multipleBeans != null) {
return multipleBeans;
}
// 查找待注入的候选者
Map<String, Object> matchingBeans = findAutowireCandidates(beanName, type, descriptor);
if (matchingBeans.isEmpty()) {
if (isRequired(descriptor)) {
raiseNoMatchingBeanFound(type, descriptor.getResolvableType(), descriptor);
}
return null;
}
String autowiredBeanName;
Object instanceCandidate;
if (matchingBeans.size() > 1) {
autowiredBeanName = determineAutowireCandidate(matchingBeans, descriptor);
if (autowiredBeanName == null) {
if (isRequired(descriptor) || !indicatesMultipleBeans(type)) {
return descriptor.resolveNotUnique(descriptor.getResolvableType(), matchingBeans);
}
else {
// In case of an optional Collection/Map, silently ignore a non-unique case:
// possibly it was meant to be an empty collection of multiple regular beans
// (before 4.3 in particular when we didn't even look for collection beans).
return null;
}
}
instanceCandidate = matchingBeans.get(autowiredBeanName);
}
else {
// 只有一个匹配到了
Map.Entry<String, Object> entry = matchingBeans.entrySet().iterator().next();
// beanName
autowiredBeanName = entry.getKey();
// beanClass 或 bean
instanceCandidate = entry.getValue();
}
if (autowiredBeanNames != null) {
autowiredBeanNames.add(autowiredBeanName);
}
if (instanceCandidate instanceof Class) {
// 解析候选者,创建依赖的 bean 实例对象
instanceCandidate = descriptor.resolveCandidate(autowiredBeanName, type, this);
}
Object result = instanceCandidate;
if (result instanceof NullBean) {
if (isRequired(descriptor)) {
raiseNoMatchingBeanFound(type, descriptor.getResolvableType(), descriptor);
}
result = null;
}
// 类型校验
if (!ClassUtils.isAssignableValue(type, result)) {
throw new BeanNotOfRequiredTypeException(autowiredBeanName, type, instanceCandidate.getClass());
}
return result;
}
finally {
ConstructorResolver.setCurrentInjectionPoint(previousInjectionPoint);
}
}
先获取依赖的类型。如果是 Field 注入, 就是字段定义的类型,此时调用 getAutowireCandidateResolver().getSuggestedValue 就能得到 @Value 注解的值。有一点需注意,如果值含有占位符,则会将包含占位符的字符串一并返回,然后利用之前注册的 embeddedValueResolvers 进行解析,得到真正的 value 值。
@Override
@Nullable
public Object getSuggestedValue(DependencyDescriptor descriptor) {
// 获取 Field 或 方法参数 上 @Value 注入的 value 值
// 如果是 Field,此处即可获取 @Value 注入的 value 值
// 如果是 Method,@Value 可存在于方法参数,也可存在于方法上,所以为 null,会获取方法注解之后,再调用 findValue
Object value = findValue(descriptor.getAnnotations());
if (value == null) {
MethodParameter methodParam = descriptor.getMethodParameter();
if (methodParam != null) {
// 获取方法上的注解,解析 @Value 注入的 value 值
value = findValue(methodParam.getMethodAnnotations());
}
}
return value;
}
// InjectionPoint
// 获取 Field 或 @Bean 方法上注解
// 针对 MethodParameter 获取的是方法参数中的注解
public Annotation[] getAnnotations() {
if (this.field != null) {
Annotation[] fieldAnnotations = this.fieldAnnotations;
if (fieldAnnotations == null) {
fieldAnnotations = this.field.getAnnotations();
this.fieldAnnotations = fieldAnnotations;
}
return fieldAnnotations;
}
else {
return obtainMethodParameter().getParameterAnnotations();
}
}
@Nullable
protected Object findValue(Annotation[] annotationsToSearch) {
if (annotationsToSearch.length > 0) {
// 获取 annotationsToSearch 中持有 @Value 注解的属性
AnnotationAttributes attr = AnnotatedElementUtils.getMergedAnnotationAttributes(
AnnotatedElementUtils.forAnnotations(annotationsToSearch), this.valueAnnotationType);
if (attr != null) {
return extractValue(attr);
}
}
return null;
}
如果是 Method 注入,则依赖的类型为方法参数类型。方法参数类型为基本类型或 String 时,通过getAutowireCandidateResolver().getSuggestedValue(descriptor); 就处理了。如果是一个 refBean,则需要 findAutowireCandidates 来处理。
// DefaultListableBeanFactory
protected Map<String, Object> findAutowireCandidates(
@Nullable String beanName, Class<?> requiredType, DependencyDescriptor descriptor) {
// 根据指定类型获取 beanFactory 中注册的 BeanDefinition 对应的 beanName
String[] candidateNames = BeanFactoryUtils.beanNamesForTypeIncludingAncestors(
this, requiredType, true, descriptor.isEager());
Map<String, Object> result = CollectionUtils.newLinkedHashMap(candidateNames.length);
// resolvableDependencies 4 个
// BeanFactory/ApplicationContext/ApplicationEventPublisher/ResourceLoader
for (Map.Entry<Class<?>, Object> classObjectEntry : this.resolvableDependencies.entrySet()) {
Class<?> autowiringType = classObjectEntry.getKey();
if (autowiringType.isAssignableFrom(requiredType)) {
Object autowiringValue = classObjectEntry.getValue();
autowiringValue = AutowireUtils.resolveAutowiringValue(autowiringValue, requiredType);
if (requiredType.isInstance(autowiringValue)) {
result.put(ObjectUtils.identityToString(autowiringValue), autowiringValue);
break;
}
}
}
for (String candidate : candidateNames) {
// 判断是否是自引用
if (!isSelfReference(beanName, candidate) && isAutowireCandidate(candidate, descriptor)) {
addCandidateEntry(result, candidate, descriptor, requiredType);
}
}
// result 不为空,直接返回 result
if (result.isEmpty()) {
boolean multiple = indicatesMultipleBeans(requiredType);
// Consider fallback matches if the first pass failed to find anything...
DependencyDescriptor fallbackDescriptor = descriptor.forFallbackMatch();
for (String candidate : candidateNames) {
if (!isSelfReference(beanName, candidate) && isAutowireCandidate(candidate, fallbackDescriptor) &&
(!multiple || getAutowireCandidateResolver().hasQualifier(descriptor))) {
addCandidateEntry(result, candidate, descriptor, requiredType);
}
}
if (result.isEmpty() && !multiple) {
// Consider self references as a final pass...
// but in the case of a dependency collection, not the very same bean itself.
for (String candidate : candidateNames) {
if (isSelfReference(beanName, candidate) &&
(!(descriptor instanceof MultiElementDescriptor) || !beanName.equals(candidate)) &&
isAutowireCandidate(candidate, fallbackDescriptor)) {
addCandidateEntry(result, candidate, descriptor, requiredType);
}
}
}
}
return result;
}
根据指定类型,即方法参数类型,获取 beanFactory 中注册的符合条件的 BeanDefinition 对应的 beanName,作为候选者名称 candidateNames。接着遍历 candidateNames,不是自引用,并且isAutowireCandidate 为 true,则执行 addCandidateEntry。
下面来看下 isAutowireCandidate 具体是如何判断的。
// DefaultListableBeanFactory
// 判断是否是注入候选者
protected boolean isAutowireCandidate(
String beanName, DependencyDescriptor descriptor, AutowireCandidateResolver resolver)
throws NoSuchBeanDefinitionException {
String bdName = BeanFactoryUtils.transformedBeanName(beanName);
if (containsBeanDefinition(bdName)) {
return isAutowireCandidate(beanName, getMergedLocalBeanDefinition(bdName), descriptor, resolver);
}
else if (containsSingleton(beanName)) {
return isAutowireCandidate(beanName, new RootBeanDefinition(getType(beanName)), descriptor, resolver);
}
BeanFactory parent = getParentBeanFactory();
if (parent instanceof DefaultListableBeanFactory) {
// No bean definition found in this factory -> delegate to parent.
return ((DefaultListableBeanFactory) parent).isAutowireCandidate(beanName, descriptor, resolver);
}
else if (parent instanceof ConfigurableListableBeanFactory) {
// If no DefaultListableBeanFactory, can't pass the resolver along.
return ((ConfigurableListableBeanFactory) parent).isAutowireCandidate(beanName, descriptor);
}
else {
return true;
}
}
protected boolean isAutowireCandidate(String beanName, RootBeanDefinition mbd,
DependencyDescriptor descriptor, AutowireCandidateResolver resolver) {
String bdName = BeanFactoryUtils.transformedBeanName(beanName);
resolveBeanClass(mbd, bdName);
if (mbd.isFactoryMethodUnique && mbd.factoryMethodToIntrospect == null) {
new ConstructorResolver(this).resolveFactoryMethodIfPossible(mbd);
}
// 创建一个 BeanDefinitionHolder
BeanDefinitionHolder holder = (beanName.equals(bdName) ?
this.mergedBeanDefinitionHolders.computeIfAbsent(beanName,
key -> new BeanDefinitionHolder(mbd, beanName, getAliases(bdName))) :
new BeanDefinitionHolder(mbd, beanName, getAliases(bdName)));
return resolver.isAutowireCandidate(holder, descriptor);
}
转化成通过注册的 ContextAnnotationAutowireCandidateResolver 来进行判断。
// QualifierAnnotationAutowireCandidateResolver
@Override
public boolean isAutowireCandidate(BeanDefinitionHolder bdHolder, DependencyDescriptor descriptor) {
boolean match = super.isAutowireCandidate(bdHolder, descriptor);
if (match) {
// 检查 @Qualifier,不存在注解,直接返回 true
match = checkQualifiers(bdHolder, descriptor.getAnnotations());
if (match) {
MethodParameter methodParam = descriptor.getMethodParameter();
if (methodParam != null) {
Method method = methodParam.getMethod();
if (method == null || void.class == method.getReturnType()) {
match = checkQualifiers(bdHolder, methodParam.getMethodAnnotations());
}
}
}
}
return match;
}
// GenericTypeAwareAutowireCandidateResolver
@Override
public boolean isAutowireCandidate(BeanDefinitionHolder bdHolder, DependencyDescriptor descriptor) {
if (!super.isAutowireCandidate(bdHolder, descriptor)) {
// If explicitly false, do not proceed with any other checks...
return false;
}
return checkGenericTypeMatch(bdHolder, descriptor);
}
// SimpleAutowireCandidateResolver
@Override
public boolean isAutowireCandidate(BeanDefinitionHolder bdHolder, DependencyDescriptor descriptor) {
return bdHolder.getBeanDefinition().isAutowireCandidate();
}
// AbstractBeanDefinition 默认 true
@Override
public boolean isAutowireCandidate() {
return this.autowireCandidate;
}
在 BeanDefinition 的抽象实现 AbstractBeanDefinition 中,autowireCandidate 默认 true。所以最终的结果就是 checkGenericTypeMatch 方法的返回值。
protected boolean checkGenericTypeMatch(BeanDefinitionHolder bdHolder, DependencyDescriptor descriptor) {
// Field 定义类型或 @Bean 方法依赖的参数类型
ResolvableType dependencyType = descriptor.getResolvableType();
if (dependencyType.getType() instanceof Class) {
// 没有泛型,不需要再次检查,直接返回
return true;
}
ResolvableType targetType = null;
boolean cacheType = false;
RootBeanDefinition rbd = null;
if (bdHolder.getBeanDefinition() instanceof RootBeanDefinition) {
rbd = (RootBeanDefinition) bdHolder.getBeanDefinition();
}
if (rbd != null) {
targetType = rbd.targetType;
if (targetType == null) {
cacheType = true;
// 首先,检查工厂方法返回类型(如果适用)
targetType = getReturnTypeForFactoryMethod(rbd, descriptor);
if (targetType == null) {
RootBeanDefinition dbd = getResolvedDecoratedDefinition(rbd);
if (dbd != null) {
targetType = dbd.targetType;
if (targetType == null) {
targetType = getReturnTypeForFactoryMethod(dbd, descriptor);
}
}
}
}
}
if (targetType == null) {
// 常规情况:直接的bean实例,BeanFactory可用。
if (this.beanFactory != null) {
Class<?> beanType = this.beanFactory.getType(bdHolder.getBeanName());
if (beanType != null) {
targetType = ResolvableType.forClass(ClassUtils.getUserClass(beanType));
}
}
// Fallback: no BeanFactory set, or no type resolvable through it
// -> best-effort match against the target class if applicable.
if (targetType == null && rbd != null && rbd.hasBeanClass() && rbd.getFactoryMethodName() == null) {
Class<?> beanClass = rbd.getBeanClass();
if (!FactoryBean.class.isAssignableFrom(beanClass)) {
targetType = ResolvableType.forClass(ClassUtils.getUserClass(beanClass));
}
}
}
if (targetType == null) {
return true;
}
if (cacheType) {
rbd.targetType = targetType;
}
if (descriptor.fallbackMatchAllowed() &&
(targetType.hasUnresolvableGenerics() || targetType.resolve() == Properties.class)) {
// Fallback matches allow unresolvable generics, e.g. plain HashMap to Map<String,String>;
// and pragmatically also java.util.Properties to any Map (since despite formally being a
// Map<Object,Object>, java.util.Properties is usually perceived as a Map<String,String>).
return true;
}
// 全面检查复杂泛型类型匹配
return dependencyType.isAssignableFrom(targetType);
}
就是对泛型的匹配,没有泛型,直接返回 true。
// DefaultListableBeanFactory
private void addCandidateEntry(Map<String, Object> candidates, String candidateName,
DependencyDescriptor descriptor, Class<?> requiredType) {
if (descriptor instanceof MultiElementDescriptor) {
Object beanInstance = descriptor.resolveCandidate(candidateName, requiredType, this);
if (!(beanInstance instanceof NullBean)) {
candidates.put(candidateName, beanInstance);
}
}
// candidateName 对应的 bean 有可能已经创建了,那么此时放入的就是已经创建的实例 bean
else if (containsSingleton(candidateName) || (descriptor instanceof StreamDependencyDescriptor &&
((StreamDependencyDescriptor) descriptor).isOrdered())) {
Object beanInstance = descriptor.resolveCandidate(candidateName, requiredType, this);
candidates.put(candidateName, (beanInstance instanceof NullBean ? null : beanInstance));
}
else {
// key beanName
// val Class
candidates.put(candidateName, getType(candidateName));
}
}
public Object resolveCandidate(String beanName, Class<?> requiredType, BeanFactory beanFactory)
throws BeansException {
return beanFactory.getBean(beanName);
}
如果依赖的 beanName 对应的 bean 实例已经创建,则 candidates 中 value 值就是 bean 实例对象,没有创建,则 value 值为依赖的 Class 对象。
处理完 findAutowireCandidates,得到待注入的候选者 matchingBeans,为空直接返回,说明没有合适的候选者。否则,为 autowiredBeanName 和 instanceCandidate 赋值。instanceCandidate 若为 Class 类型,表明依赖的 bean 实例对象还未创建,调用 resolveCandidate 进行实例的创建。
这样,就完成了 spring 注解模式下对依赖的解析。