SpringloC容器的依赖注入源码解析(10)—— populateBean的剩余逻辑

本文阅读 16 分钟
首页 代码,Java 正文

populateBean的前置逻辑文章

img

protected void populateBean(String beanName, RootBeanDefinition mbd, @Nullable BeanWrapper bw) { 
        if (bw == null) { 
            if (mbd.hasPropertyValues()) { 
                throw new BeanCreationException(
                        mbd.getResourceDescription(), beanName, "Cannot apply property values to null instance");
            }
            else { 
                // Skip property population phase for null instance.
                return;
            }
        }

        // Give any InstantiationAwareBeanPostProcessors the opportunity to modify the
        // state of the bean before properties are set. This can be used, for example,
        // to support styles of field injection.
        boolean continueWithPropertyPopulation = true;

        if (!mbd.isSynthetic() && hasInstantiationAwareBeanPostProcessors()) { 
            for (BeanPostProcessor bp : getBeanPostProcessors()) { 
                if (bp instanceof InstantiationAwareBeanPostProcessor) { 
                    InstantiationAwareBeanPostProcessor ibp = (InstantiationAwareBeanPostProcessor) bp;
                    if (!ibp.postProcessAfterInstantiation(bw.getWrappedInstance(), beanName)) { 
                        continueWithPropertyPopulation = false;
                        break;
                    }
                }
            }
        }

        // 如果上面设置continueWithPropertyPopulation = false,表明用户可能已经自己填充了
        // bean的属性,不需要Spring帮忙填充了。此时直接返回即可
        if (!continueWithPropertyPopulation) { 
            return;
        }
        // pvs是一个MutablePropertyValues实例,里面实现了PropertyValues接口,
        // 提供属性的读写操作实现,同时可以通过调用构造函数实现深拷贝
        // 获取BeanDefinition里面为Bean设置上的属性值
        PropertyValues pvs = (mbd.hasPropertyValues() ? mbd.getPropertyValues() : null);

        int resolvedAutowireMode = mbd.getResolvedAutowireMode();
        if (resolvedAutowireMode == AUTOWIRE_BY_NAME || resolvedAutowireMode == AUTOWIRE_BY_TYPE) { 
            MutablePropertyValues newPvs = new MutablePropertyValues(pvs);
            // Add property values based on autowire by name if applicable.
            if (resolvedAutowireMode == AUTOWIRE_BY_NAME) { 
                autowireByName(beanName, mbd, bw, newPvs);
            }
            // Add property values based on autowire by type if applicable.
            if (resolvedAutowireMode == AUTOWIRE_BY_TYPE) { 
                autowireByType(beanName, mbd, bw, newPvs);
            }
            pvs = newPvs;
        }

        boolean hasInstAwareBpps = hasInstantiationAwareBeanPostProcessors();
        boolean needsDepCheck = (mbd.getDependencyCheck() != AbstractBeanDefinition.DEPENDENCY_CHECK_NONE);

        PropertyDescriptor[] filteredPds = null;
        if (hasInstAwareBpps) { 
            if (pvs == null) { 
                pvs = mbd.getPropertyValues();
            }
            for (BeanPostProcessor bp : getBeanPostProcessors()) { 
                if (bp instanceof InstantiationAwareBeanPostProcessor) { 
                    InstantiationAwareBeanPostProcessor ibp = (InstantiationAwareBeanPostProcessor) bp;
                    // 在这里会对@Autowired标记的属性进行依赖注入
                    PropertyValues pvsToUse = ibp.postProcessProperties(pvs, bw.getWrappedInstance(), beanName);
                    if (pvsToUse == null) { 
                        if (filteredPds == null) { 
                            filteredPds = filterPropertyDescriptorsForDependencyCheck(bw, mbd.allowCaching);
                        }
                        pvsToUse = ibp.postProcessPropertyValues(pvs, filteredPds, bw.getWrappedInstance(), beanName);
                        if (pvsToUse == null) { 
                            return;
                        }
                    }
                    pvs = pvsToUse;
                }
            }
        }
        // 依赖检查,对应depend-on属性,3.0已经弃用此属性
        if (needsDepCheck) { 
            // 过滤出所有需要进行依赖检查的属性编辑器
            if (filteredPds == null) { 
                filteredPds = filterPropertyDescriptorsForDependencyCheck(bw, mbd.allowCaching);
            }
            checkDependencies(beanName, mbd, filteredPds, pvs);
        }

        if (pvs != null) { 
            // 最终将属性注入到Bean的Wrapper实例里,这里的注入主要是供
            // 显式配置了autowiredbyName或者ByType的属性注入,
            // 针对注解来讲,由于在AutowiredAnnotationBeanPostProcessor已经完成了注入,
            // 所以此处不执行
            applyPropertyValues(beanName, mbd, bw, pvs);
        }
    }

完成了按名字或按类型自动装配后,来到脑图里第三步,对解析完但还未设置的属性进行再处理。

img 这里需要关注AutowiredAnnotationBeanPostProcessor实现的postProcessProperties方法

@Override
public PropertyValues postProcessProperties(PropertyValues pvs, Object bean, String beanName) { 
   // 获取指定类中@Autowired相关注解的元信息
   InjectionMetadata metadata = findAutowiringMetadata(beanName, bean.getClass(), pvs);
   try { 
      // 对Bean的属性进行自动注入
      metadata.inject(bean, beanName, pvs);
   }
   catch (BeanCreationException ex) { 
      throw ex;
   }
   catch (Throwable ex) { 
      throw new BeanCreationException(beanName, "Injection of autowired dependencies failed", ex);
   }
   return pvs;
}

首先会去尝试获取InjectionMetadata对象,findAutowiringMetadata方法之前在分析该类的postProcessMergedBeanDefinition方法时,已经获取到了存储有该bean实例里被@Autowired或@Value标签修饰的属性列表的InjectionMetaData对象,并且将其已经放置到了缓存中。再次进入findAutowiringMetadata

img 在此次调用时,相关的InjectionMetadata实例已经从缓存中获取到了,不需要再进到if里面去解析bean了,此时又回到postProcessProperties方法里,取到了InjectionMetadata实例之后直接对bean注入属性

metadata.inject(bean, beanName, pvs);
public void inject(Object target, @Nullable String beanName, @Nullable PropertyValues pvs) throws Throwable { 
   Collection<InjectedElement> checkedElements = this.checkedElements;
   // 要注入的字段集合
   Collection<InjectedElement> elementsToIterate =
         (checkedElements != null ? checkedElements : this.injectedElements);
   if (!elementsToIterate.isEmpty()) { 
      // 遍历每个字段并进行注入
      for (InjectedElement element : elementsToIterate) { 
         if (logger.isTraceEnabled()) { 
            logger.trace("Processing injected element of bean '" + beanName + "': " + element);
         }
         element.inject(target, beanName, pvs);
      }
   }
}

该方法遍历每一个属性元素去调用元素的inject方法,进入inject发现又回到了AutowiredAnnotationBeanPostProcessor类里:

@Override
protected void inject(Object bean, @Nullable String beanName, @Nullable PropertyValues pvs) throws Throwable { 
     // 获取要注入的成员变量
     Field field = (Field) this.member;
     Object value;
     // 如果成员变量的值先前缓存过
     if (this.cached) { 
        // 从缓存中获取成员变量的值
        value = resolvedCachedArgument(beanName, this.cachedFieldValue);
     }
     // 没有缓存
     else { 
        // 创建一个成员变量的依赖描述符实例
        DependencyDescriptor desc = new DependencyDescriptor(field, this.required);
        desc.setContainingClass(bean.getClass());
        Set<String> autowiredBeanNames = new LinkedHashSet<>(1);
        Assert.state(beanFactory != null, "No BeanFactory available");
        // 获取容器的类型转换器
        TypeConverter typeConverter = beanFactory.getTypeConverter();
        try { 
           // 获取注入的值
           value = beanFactory.resolveDependency(desc, beanName, autowiredBeanNames, typeConverter);
        }
        catch (BeansException ex) { 
           throw new UnsatisfiedDependencyException(null, beanName, new InjectionPoint(field), ex);
        }
        synchronized (this) { 
           if (!this.cached) { 
              if (value != null || this.required) { 
                 this.cachedFieldValue = desc;
                 registerDependentBeans(beanName, autowiredBeanNames);
                 if (autowiredBeanNames.size() == 1) { 
                    String autowiredBeanName = autowiredBeanNames.iterator().next();
                    if (beanFactory.containsBean(autowiredBeanName) &&
                          beanFactory.isTypeMatch(autowiredBeanName, field.getType())) { 
                       this.cachedFieldValue = new ShortcutDependencyDescriptor(
                             desc, autowiredBeanName, field.getType());
                    }
                 }
              }
              else { 
                 this.cachedFieldValue = null;
              }
              this.cached = true;
           }
        }
     }
     if (value != null) { 
        ReflectionUtils.makeAccessible(field);
        field.set(bean, value);
     }
  }
}

在调用的过程中复用了其他类的装配能力,此时是给boyfriend装配上girlfriend实例,首先去缓存里看下之前是否解析过girlfriend,第一次执行会进入到else里,先用DependencyDescriptor包装一下属性field:

DependencyDescriptor desc = new DependencyDescriptor(field, this.required);

之后给desc注册上宿主的类名(Boyfriend):

desc.setContainingClass(bean.getClass());

之后会尝试获取之前容器初始化时注册上去的转换器TypeConverter:

TypeConverter typeConverter = beanFactory.getTypeConverter();

converter用来做类型转换,默认获取spring自带的simpleTypeConverter用来处理简单类型的转换,之后执行

// 获取注入的值
value = beanFactory.resolveDependency(desc, beanName, autowiredBeanNames, typeConverter);

进入resolveDependency方法里:

@Override
@Nullable
public Object resolveDependency(DependencyDescriptor descriptor, @Nullable String requestingBeanName,
      @Nullable Set<String> autowiredBeanNames, @Nullable TypeConverter typeConverter) throws BeansException { 

   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 { 
      Object result = getAutowireCandidateResolver().getLazyResolutionProxyIfNecessary(
            descriptor, requestingBeanName);
      if (result == null) { 
         result = doResolveDependency(descriptor, requestingBeanName, autowiredBeanNames, typeConverter);
      }
      return result;
   }
}

在方法里会依据依赖描述符的不同类型进行不同的处理,但是最终都会到else里,真正起作用的是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 { 
      // 该方法最终调用了beanFactory.getBean(String, Class),从容器中获取依赖
      Object shortcut = descriptor.resolveShortcut(this);
      // 如果容器缓存中存在所需依赖,这里进行短路路操作,提前结束依赖解析逻辑
      if (shortcut != null) { 
         return shortcut;
      }

      Class<?> type = descriptor.getDependencyType();
      // 处理@Value注解
      Object value = getAutowireCandidateResolver().getSuggestedValue(descriptor);
      if (value != null) { 
         if (value instanceof String) { 
            String strVal = resolveEmbeddedValue((String) value);
            BeanDefinition bd = (beanName != null && containsBean(beanName) ?
                  getMergedBeanDefinition(beanName) : null);
            value = evaluateBeanDefinitionString(strVal, bd);
         }
         TypeConverter converter = (typeConverter != null ? typeConverter : getTypeConverter());
         try { 
            return converter.convertIfNecessary(value, type, descriptor.getTypeDescriptor());
         }
         catch (UnsupportedOperationException ex) { 
            // A custom TypeConverter which does not support TypeDescriptor resolution...
            return (descriptor.getField() != null ?
                  converter.convertIfNecessary(value, type, descriptor.getField()) :
                  converter.convertIfNecessary(value, type, descriptor.getMethodParameter()));
         }
      }
      // 如果标识@Autowired注解的成员变量是复合类型,如Array,Collection,Map
      // 从这个方法获取@Autowired里的值
      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 { 
         // We have exactly one match.
         Map.Entry<String, Object> entry = matchingBeans.entrySet().iterator().next();
         autowiredBeanName = entry.getKey();
         instanceCandidate = entry.getValue();
      }

      if (autowiredBeanNames != null) { 
         autowiredBeanNames.add(autowiredBeanName);
      }
      if (instanceCandidate instanceof Class) { 
         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);
   }
}

首先尝试调用依赖描述符实例的resolveShortcut方法,尝试从容器缓存里获取属性名对应的bean实例

@Nullable
public Object resolveShortcut(BeanFactory beanFactory) throws BeansException { 
   return null;
}

相对于注解的这种情况,并没有实现该方法。

之后尝试从依赖描述符实例里面去获取目标实例的属性

Class<?> type = descriptor.getDependencyType();

这里的目标实例是girlfriend,之后就会调用注解候选解析器的getSuggestedValue方法尝试获取属性值,但是对于@Autowired修饰的属性来说,这一步无法获取到值

@Override
@Nullable
public Object getSuggestedValue(DependencyDescriptor descriptor) { 
   Object value = findValue(descriptor.getAnnotations());
   if (value == null) { 
      MethodParameter methodParam = descriptor.getMethodParameter();
      if (methodParam != null) { 
         value = findValue(methodParam.getMethodAnnotations());
      }
   }
   return value;
}

该方法调用findValue方法

@Nullable
protected Object findValue(Annotation[] annotationsToSearch) { 
   if (annotationsToSearch.length > 0) {    // qualifier annotations have to be local
      AnnotationAttributes attr = AnnotatedElementUtils.getMergedAnnotationAttributes(
            AnnotatedElementUtils.forAnnotations(annotationsToSearch), this.valueAnnotationType);
      if (attr != null) { 
         return extractValue(attr);
      }
   }
   return null;
}

该方法主要是提取@Value修饰的属性值的

回到doResolveDependency方法 img 在if里会视情况对获取到的value进行类型转换。

之后来到resolveMultipleBeans方法

// 如果标识@Autowired注解的成员变量是复合类型,如Array,Collection,Map
// 从这个方法获取@Autowired里的值
Object multipleBeans = resolveMultipleBeans(descriptor, beanName, autowiredBeanNames, typeConverter);
@Nullable
private Object resolveMultipleBeans(DependencyDescriptor descriptor, @Nullable String beanName,
      @Nullable Set<String> autowiredBeanNames, @Nullable TypeConverter typeConverter) { 

   final Class<?> type = descriptor.getDependencyType();
   // 首先是stream类型的处理
   if (descriptor instanceof StreamDependencyDescriptor) { 
      Map<String, Object> matchingBeans = findAutowireCandidates(beanName, type, descriptor);
      if (autowiredBeanNames != null) { 
         autowiredBeanNames.addAll(matchingBeans.keySet());
      }
      Stream<Object> stream = matchingBeans.keySet().stream()
            .map(name -> descriptor.resolveCandidate(name, type, this))
            .filter(bean -> !(bean instanceof NullBean));
      if (((StreamDependencyDescriptor) descriptor).isOrdered()) { 
         stream = stream.sorted(adaptOrderComparator(matchingBeans));
      }
      return stream;
   }
   // 判断要注入的是不是一个数组,可见除了集合注入外,也可以以数组的形式注入bean
   else if (type.isArray()) { 
      Class<?> componentType = type.getComponentType();
      ResolvableType resolvableType = descriptor.getResolvableType();
      Class<?> resolvedArrayType = resolvableType.resolve(type);
      if (resolvedArrayType != type) { 
         componentType = resolvableType.getComponentType().resolve();
      }
      if (componentType == null) { 
         return null;
      }
      Map<String, Object> matchingBeans = findAutowireCandidates(beanName, componentType,
            new MultiElementDescriptor(descriptor));
      if (matchingBeans.isEmpty()) { 
         return null;
      }
      if (autowiredBeanNames != null) { 
         autowiredBeanNames.addAll(matchingBeans.keySet());
      }
      TypeConverter converter = (typeConverter != null ? typeConverter : getTypeConverter());
      Object result = converter.convertIfNecessary(matchingBeans.values(), resolvedArrayType);
      if (result instanceof Object[]) { 
         Comparator<Object> comparator = adaptDependencyComparator(matchingBeans);
         if (comparator != null) { 
            Arrays.sort((Object[]) result, comparator);
         }
      }
      return result;
   }
   // 判断注入的是不是集合的接口类(List,Set等)
   else if (Collection.class.isAssignableFrom(type) && type.isInterface()) { 
      Class<?> elementType = descriptor.getResolvableType().asCollection().resolveGeneric();
      if (elementType == null) { 
         return null;
      }
      Map<String, Object> matchingBeans = findAutowireCandidates(beanName, elementType,
            new MultiElementDescriptor(descriptor));
      if (matchingBeans.isEmpty()) { 
         return null;
      }
      if (autowiredBeanNames != null) { 
         autowiredBeanNames.addAll(matchingBeans.keySet());
      }
      TypeConverter converter = (typeConverter != null ? typeConverter : getTypeConverter());
      Object result = converter.convertIfNecessary(matchingBeans.values(), type);
      if (result instanceof List) { 
         Comparator<Object> comparator = adaptDependencyComparator(matchingBeans);
         if (comparator != null) { 
            ((List<?>) result).sort(comparator);
         }
      }
      return result;
   }
   // 判断要注入的是不是map类
   else if (Map.class == type) { 
      ResolvableType mapType = descriptor.getResolvableType().asMap();
      Class<?> keyType = mapType.resolveGeneric(0);
      if (String.class != keyType) { 
         return null;
      }
      Class<?> valueType = mapType.resolveGeneric(1);
      if (valueType == null) { 
         return null;
      }
      Map<String, Object> matchingBeans = findAutowireCandidates(beanName, valueType,
            new MultiElementDescriptor(descriptor));
      if (matchingBeans.isEmpty()) { 
         return null;
      }
      if (autowiredBeanNames != null) { 
         autowiredBeanNames.addAll(matchingBeans.keySet());
      }
      return matchingBeans;
   }
   else { 
      return null;
   }
}

该方法主要是针对复合类型(stream类型、数组类型、集合类型、map类型)的值进行解析处理,无论是哪种复合类型,最终都会调用findAutowireCandidates方法去获取注入的候选者列表(可能有多个)

由于测试时并非用的复合类型的数据,所以此处的multipleBeans为空

回到doResolveDependency,继续执行后续的逻辑

// 如果标识@Autowired注解的属性是非复合类型
// 从这个方法获取@Autowired里的值
Map<String, Object> matchingBeans = findAutowireCandidates(beanName, type, descriptor);
if (matchingBeans.isEmpty()) { 
   // 没有找到,检验@Autowire的require是否为true
   if (isRequired(descriptor)) { 
      raiseNoMatchingBeanFound(type, descriptor.getResolvableType(), descriptor);
   }
   return null;
}

  处理被@Autowired标记的非复合类型的逻辑,同样会调用处理复合逻辑类型里的findAutowireCandidates方法尝试从容器里面根据属性的类型获取到对应的bean名字,

protected Map<String, Object> findAutowireCandidates(
      @Nullable String beanName, Class<?> requiredType, DependencyDescriptor descriptor) { 
   // 查找出所有符合类型的beanName
   String[] candidateNames = BeanFactoryUtils.beanNamesForTypeIncludingAncestors(
         this, requiredType, true, descriptor.isEager());
   Map<String, Object> result = new LinkedHashMap<>(candidateNames.length);
   // resolvableDependencies记录了属性类型--值的映射
   for (Map.Entry<Class<?>, Object> classObjectEntry : this.resolvableDependencies.entrySet()) { 
      Class<?> autowiringType = classObjectEntry.getKey();
      if (autowiringType.isAssignableFrom(requiredType)) { 
         Object autowiringValue = classObjectEntry.getValue();
         // key值是我们需要的类型
         autowiringValue = AutowireUtils.resolveAutowiringValue(autowiringValue, requiredType);
         if (requiredType.isInstance(autowiringValue)) { 
            result.put(ObjectUtils.identityToString(autowiringValue), autowiringValue);
            break;
         }
      }
   }
   // 遍历候选数组
    for (String candidate : candidateNames) { 
       // 候选Bean不是自引用(即要注入的类不能是类本身,会触发无限递归注入)
       if (!isSelfReference(beanName, candidate) && isAutowireCandidate(candidate, descriptor)) { 
          addCandidateEntry(result, candidate, descriptor, requiredType);
       }
    }
   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;
}

首先调用BeanFactoryUtils.beanNamesForTypeIncludingAncestors,尝试获取针对于该属性的候选名单,beanNamesForTypeIncludingAncestors会尝试从各层容器里寻找符合该属性类型的bean的名字。

Map<String, Object> result会存放girlfriend。

之后会尝试去从已经注册到容器里的依赖关系里,去寻找先前有没有注入过girlfriend属性的依赖,这里相当于缓存的作用,由于是第一次所以肯定没有。

之后for循环会轮询候选列表做一些必要的检查,过滤掉自己依赖于自己的,再看看是否是支持注入的,满足条件就将其添加到候选人的列表当中

之后如果result为空的话会对依赖描述符做一个降级处理(一般进不来这个逻辑里)

DependencyDescriptor fallbackDescriptor = descriptor.forFallbackMatch();

这一步可以理解为在容器里找不到和当前类型匹配的bean时,会尝试去到可以替代该类的类中查找,比如girlfriend的父类看看能不能找到候选者

回到doResolveDependency,如果选出的bean个数大于1的话,就会选出最佳的候选者

if (matchingBeans.size() > 1) { 
   // 如果被@Autowired标记的有两个以上同样的类型。
   // 就需要依据@Primary以及@Priority注解标签选择了
   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);
}

进入到determineAutowireCandidate方法,用于选择最佳的候选bean:

@Nullable
protected String determineAutowireCandidate(Map<String, Object> candidates, DependencyDescriptor descriptor) { 
   Class<?> requiredType = descriptor.getDependencyType();
   // 根据@Primary注解标签来选择最优解
   String primaryCandidate = determinePrimaryCandidate(candidates, requiredType);
   if (primaryCandidate != null) { 
      return primaryCandidate;
   }
   // 根据@Order,@PriorityOrder,及实现Order接口的序号来选择最优解,选序号最小的
   String priorityCandidate = determineHighestPriorityCandidate(candidates, requiredType);
   if (priorityCandidate != null) { 
      return priorityCandidate;
   }
   // Fallback
   for (Map.Entry<String, Object> entry : candidates.entrySet()) { 
      String candidateName = entry.getKey();
      Object beanInstance = entry.getValue();
      if ((beanInstance != null && this.resolvableDependencies.containsValue(beanInstance)) ||
            matchesBeanName(candidateName, descriptor.getDependencyName())) { 
         return candidateName;
      }
   }
   return null;
}
  1. 先找候选bean里是否有被@Primary标记的,有则直接选择;
  2. 没有的话再据@Order,@PriorityOrder,及实现Order接口的序号来选择最优解,选序号最小的;
  3. 没有的话降级看看有没有合适的bean,用属性的名字或别名找有没有相关的bean返回。

从上面的逻辑可以看出,@Autowired并非一定按照类型来查找。

回到doResolveDependency,由于在我们的例子里只有一个候选者,所以会来到else

else { 
   // We have exactly one match.
   Map.Entry<String, Object> entry = matchingBeans.entrySet().iterator().next();
   autowiredBeanName = entry.getKey();
   instanceCandidate = entry.getValue();
}

在这里会获取到对应的属性名,以及属性对应的class对象,此时只是拿到了girlfriend的名字和class,还没有创建出其实例,因为在最终确认之前没必要创建多余的bean实例。

之后调用resolveCandidate去解析类的实例:

if (instanceCandidate instanceof Class) { 
   instanceCandidate = descriptor.resolveCandidate(autowiredBeanName, type, this);
}
public Object resolveCandidate(String beanName, Class<?> requiredType, BeanFactory beanFactory)
      throws BeansException { 

   return beanFactory.getBean(beanName);
}

所谓的解析其实就是根据bean的名字去调用容器的getBean方法去获取/创建出bean实例,如果经过aop包装的话,获取出的属性也会是经过aop包装的。

剩下后续就是一些验证了逻辑了,验证完之后就执行完成整个doResolveDependency方法了,此时resolveDependency方法就获得了girlfriend对应的bean实例了,再上一层回到AutowiredAnnotationBeanPostProcessor的inject方法执行的地方,获取到girlfriend的bean实例之后,就会去注册相关的依赖关系 img

synchronized (this) { 
   if (!this.cached) { 
      // 成员变量的值不为null,并且required属性为true
      if (value != null || this.required) { 
         this.cachedFieldValue = desc;
         // 为指定Bean注册依赖Bean
         registerDependentBeans(beanName, autowiredBeanNames);
         if (autowiredBeanNames.size() == 1) { 
            String autowiredBeanName = autowiredBeanNames.iterator().next();
            // 如果容器中有指定名称的Bean对象
            if (beanFactory.containsBean(autowiredBeanName) &&
                  // 依赖对象类型和字段类型匹配,默认按类型注入
                  beanFactory.isTypeMatch(autowiredBeanName, field.getType())) { 
               this.cachedFieldValue = new ShortcutDependencyDescriptor(
                     desc, autowiredBeanName, field.getType());
            }
         }
      }
      else { 
         this.cachedFieldValue = null;
      }
      this.cached = true;
   }
}

注册完依赖关系后就会将bean实例放入到缓存里,在inject方法最后就是调用反射机制来给field设置上该bean实例了

// 如果字段值不为null
if (value != null) { 
   // 使用反射机制来赋值
   ReflectionUtils.makeAccessible(field);
   field.set(bean, value);
}

之后回到AbstractAutowireCapableBeanFactory的populateBean方法

// 在这里会对@Autowired标记的属性进行依赖注入
PropertyValues pvsToUse = ibp.postProcessProperties(pvs, bw.getWrappedInstance(), beanName);

这时这里执行完毕了,boyfriend就会设置上girlfriend的bean实例,接下来来到依赖检查,

// 依赖检查,对应depend-on属性,3.0已经弃用此属性
if (needsDepCheck) { 
   // 过滤出所有需要进行依赖检查的属性编辑器
   if (filteredPds == null) { 
      filteredPds = filterPropertyDescriptorsForDependencyCheck(bw, mbd.allowCaching);
   }
   checkDependencies(beanName, mbd, filteredPds, pvs);
}

这里是对显式指定depends-on来检查的,默认不开启,所以会来到

if (pvs != null) { 
   // 最终将属性注入到Bean的Wrapper实例里,这里的注入主要是供
   // 显式配置了autowiredbyName或者ByType的属性注入,
   // 针对注解来讲,由于在AutowiredAnnotationBeanPostProcessor已经完成了注入,
   // 所以此处不执行
   applyPropertyValues(beanName, mbd, bw, pvs);
}

进入到applyPropertyValues方法里:

protected void applyPropertyValues(String beanName, BeanDefinition mbd, BeanWrapper bw, PropertyValues pvs) { 
   if (pvs.isEmpty()) { 
      return;
   }

   if (System.getSecurityManager() != null && bw instanceof BeanWrapperImpl) { 
      // 设置安全上下文,JDK安全机制
      ((BeanWrapperImpl) bw).setSecurityContext(getAccessControlContext());
   }

   MutablePropertyValues mpvs = null;
   List<PropertyValue> original;

   if (pvs instanceof MutablePropertyValues) { 
      mpvs = (MutablePropertyValues) pvs;
      if (mpvs.isConverted()) { 
         // Shortcut: use the pre-converted values as-is.
         // 若属性值已经转换了,则直接赋值
         try { 
            bw.setPropertyValues(mpvs);
            return;
         }
         catch (BeansException ex) { 
            throw new BeanCreationException(
                  mbd.getResourceDescription(), beanName, "Error setting property values", ex);
         }
      }
      // 若没有被转换,先将没转换前的原始类型值给记录下来
      original = mpvs.getPropertyValueList();
   }
   else { 
      // 如果pvs不是MutablePropertyValues类型,则直接使用原始类型
      original = Arrays.asList(pvs.getPropertyValues());
   }
   // 获取用户的自定义类型转换
   TypeConverter converter = getCustomTypeConverter();
   if (converter == null) { 
      converter = bw;
   }
   // 创建一个Bean定义属性值解析器,将BeanDefinition中的属性值解析为Bean实例对象的实际值
   BeanDefinitionValueResolver valueResolver = new BeanDefinitionValueResolver(this, beanName, mbd, converter);

   // Create a deep copy, resolving any references for values.
   // 为属性需要解析的值创建一个副本,将副本的数据注入Bean实例
   List<PropertyValue> deepCopy = new ArrayList<>(original.size());
   boolean resolveNecessary = false;
   for (PropertyValue pv : original) { 
      // 不需要转换的属性值直接添加
      if (pv.isConverted()) { 
         deepCopy.add(pv);
      }
      else { 
         String propertyName = pv.getName();
         // 保留转换前的属性值
         Object originalValue = pv.getValue();
         // 如果是被Autowired标记的实例,则把Bean里面关于set此属性的方法给记录下来,
         if (originalValue == AutowiredPropertyMarker.INSTANCE) { 
            Method writeMethod = bw.getPropertyDescriptor(propertyName).getWriteMethod();
            if (writeMethod == null) { 
               throw new IllegalArgumentException("Autowire marker for property without write method: " + pv);
            }
            originalValue = new DependencyDescriptor(new MethodParameter(writeMethod, 0), true);
         }
         Object resolvedValue = valueResolver.resolveValueIfNecessary(pv, originalValue);
         Object convertedValue = resolvedValue;
         boolean convertible = bw.isWritableProperty(propertyName) &&
               !PropertyAccessorUtils.isNestedOrIndexedProperty(propertyName);
         if (convertible) { 
            convertedValue = convertForProperty(resolvedValue, propertyName, bw, converter);
         }
         // Possibly store converted value in merged bean definition,
         // in order to avoid re-conversion for every created bean instance.
         if (resolvedValue == originalValue) { 
            if (convertible) { 
               pv.setConvertedValue(convertedValue);
            }
            deepCopy.add(pv);
         }
         else if (convertible && originalValue instanceof TypedStringValue &&
               !((TypedStringValue) originalValue).isDynamic() &&
               !(convertedValue instanceof Collection || ObjectUtils.isArray(convertedValue))) { 
            pv.setConvertedValue(convertedValue);
            deepCopy.add(pv);
         }
         else { 
            resolveNecessary = true;
            deepCopy.add(new PropertyValue(pv, convertedValue));
         }
      }
   }
   if (mpvs != null && !resolveNecessary) { 
      mpvs.setConverted();
   }

   // Set our (possibly massaged) deep copy.
   try { 
      // 进行属性的依赖注入
      bw.setPropertyValues(new MutablePropertyValues(deepCopy));
   }
   catch (BeansException ex) { 
      throw new BeanCreationException(
            mbd.getResourceDescription(), beanName, "Error setting property values", ex);
   }
}

针对注解的情况,直接返回

if (pvs.isEmpty()) { 
   return;
}

该方法主要是视情况做各种属性值的类型转换,毕竟获取到的是字符串类型的Type,需要这些字符串的type转换成对应的类型,首先看一下缓存里有没有,如果没有再做转换,转换完成后最终会调用

bw.setPropertyValues(new MutablePropertyValues(deepCopy));

给bean设置上属性值。

回到AbstractAutowireCapableBeanFactory的doCreateBean方法,执行完

populateBean(beanName, mbd, instanceWrapper);

之后调用

// 初始化bean,过程如下:
// 1. 判断是否实现了BeanNameAware,BeanClassLoaderAware
// BeanFactoryAware方法,如果有,则设置相关的属性
// 2. 调用bean初始化的前置(BeanPostProcessor)操作
// 3. 执行初始化的方法
// 如果有initializingBean,则调用afterPropertiesSet
// 如果有InitMethod,则调用初始方法
// 4. 调用bean初始化的后置(BeanPostProcessor)操作
exposedObject = initializeBean(beanName, exposedObject, mbd);
protected Object initializeBean(final String beanName, final Object bean, @Nullable RootBeanDefinition mbd) { 
   if (System.getSecurityManager() != null) { 
      AccessController.doPrivileged((PrivilegedAction<Object>) () -> { 
         invokeAwareMethods(beanName, bean);
         return null;
      }, getAccessControlContext());
   }
   else { 
      invokeAwareMethods(beanName, bean);
   }

   Object wrappedBean = bean;
   if (mbd == null || !mbd.isSynthetic()) { 
      wrappedBean = applyBeanPostProcessorsBeforeInitialization(wrappedBean, beanName);
   }

   try { 
      invokeInitMethods(beanName, wrappedBean, mbd);
   }
   catch (Throwable ex) { 
      throw new BeanCreationException(
            (mbd != null ? mbd.getResourceDescription() : null),
            beanName, "Invocation of init method failed", ex);
   }
   if (mbd == null || !mbd.isSynthetic()) { 
      wrappedBean = applyBeanPostProcessorsAfterInitialization(wrappedBean, beanName);
   }

   return wrappedBean;
}

跳过前面检查的逻辑之后执行

invokeAwareMethods(beanName, bean);
private void invokeAwareMethods(final String beanName, final Object bean) { 
   if (bean instanceof Aware) { 
      if (bean instanceof BeanNameAware) { 
         ((BeanNameAware) bean).setBeanName(beanName);
      }
      if (bean instanceof BeanClassLoaderAware) { 
         ClassLoader bcl = getBeanClassLoader();
         if (bcl != null) { 
            ((BeanClassLoaderAware) bean).setBeanClassLoader(bcl);
         }
      }
      if (bean instanceof BeanFactoryAware) { 
         ((BeanFactoryAware) bean).setBeanFactory(AbstractAutowireCapableBeanFactory.this);
      }
   }
}

该方法判断bean是否实现了相关的一些bean级别的Aware接口的set方法,如果实现了就将其set进去

回到initializeBean,执行完

invokeAwareMethods(beanName, bean);

之后就会判断

if (mbd == null || !mbd.isSynthetic()) { 
   wrappedBean = applyBeanPostProcessorsAfterInitialization(wrappedBean, beanName);
}

如果bean实例不是spring内置的一些特殊的bean,就会调用applyBeanPostProcessorsAfterInitialization方法去处理

@Override
public Object applyBeanPostProcessorsAfterInitialization(Object existingBean, String beanName)
      throws BeansException { 

   Object result = existingBean;
   for (BeanPostProcessor processor : getBeanPostProcessors()) { 
      Object current = processor.postProcessAfterInitialization(result, beanName);
      if (current == null) { 
         return result;
      }
      result = current;
   }
   return result;
}

发现该方法又使用了责任链模式,此时调用的是通用的bean后置处理器

Object current = processor.postProcessAfterInitialization(result, beanName);

此时该方法的执行节点是在bean构造完成之后,并且bean里面的初始化方法InitMethod被执行之前,在该责任链中,如果其中某个processor处理之后为空则中止执行,同时会返回最近的一个processor对bean处理的结果

回到initializeBean方法里,接下来会执行

invokeInitMethods(beanName, wrappedBean, mbd);
protected void invokeInitMethods(String beanName, final Object bean, @Nullable RootBeanDefinition mbd)
      throws Throwable { 
    // 如果当前bean是InitializingBean类型的 && afterPropertiesSet这个方法没有注册为外部管理的初始化方法
    // 就回调afterPropertiesSet方法
   boolean isInitializingBean = (bean instanceof InitializingBean);
   if (isInitializingBean && (mbd == null || !mbd.isExternallyManagedInitMethod("afterPropertiesSet"))) { 
      if (logger.isTraceEnabled()) { 
         logger.trace("Invoking afterPropertiesSet() on bean with name '" + beanName + "'");
      }
      if (System.getSecurityManager() != null) { 
         try { 
            AccessController.doPrivileged((PrivilegedExceptionAction<Object>) () -> { 
               ((InitializingBean) bean).afterPropertiesSet();
               return null;
            }, getAccessControlContext());
         }
         catch (PrivilegedActionException pae) { 
            throw pae.getException();
         }
      }
      else { 
         ((InitializingBean) bean).afterPropertiesSet();
      }
   }

   if (mbd != null && bean.getClass() != NullBean.class) { 
      String initMethodName = mbd.getInitMethodName();
      // 如果设置了initMethod方法的话也会执行用户配置的初始话方法
      // 并且这个类不是InitializingBean类型和不是afterPropertiesSet方法;
      // 才能执行用户配置的方法
      // 样例<bean id="person" class="com.wjw.Person" init-method="init" destroy-method="destory"/>
      if (StringUtils.hasLength(initMethodName) &&
            !(isInitializingBean && "afterPropertiesSet".equals(initMethodName)) &&
            !mbd.isExternallyManagedInitMethod(initMethodName)) { 
         invokeCustomInitMethod(beanName, bean, mbd);
      }
   }
}

先判断bean是否实现了InitializingBean这个初始化接口,如果实现了里面的afterPropertiesSet方法就会调用实现类里面的该方法进行一些初始化操作,

((InitializingBean) bean).afterPropertiesSet();

如果没有实现的话,就会去看是否指定了和注释样例里一样的init-method属性,有的话就执行对应的方法

回到initializeBean方法里,之后执行:

if (mbd == null || !mbd.isSynthetic()) { 
   wrappedBean = applyBeanPostProcessorsAfterInitialization(wrappedBean, beanName);
}
@Override
public Object applyBeanPostProcessorsAfterInitialization(Object existingBean, String beanName)
      throws BeansException { 

   Object result = existingBean;
   for (BeanPostProcessor processor : getBeanPostProcessors()) { 
      Object current = processor.postProcessAfterInitialization(result, beanName);
      if (current == null) { 
         return result;
      }
      result = current;
   }
   return result;
}

同样也是执行通用的BeanPostProcessor逻辑,只要有一次结果是空就返回,postProcessAfterInitialization是spring aop的核心,之后会专门分析。

本文为互联网自动采集或经作者授权后发布,本文观点不代表立场,若侵权下架请联系我们删帖处理!文章出自:https://wangjiawei.blog.csdn.net/article/details/121565006
-- 展开阅读全文 --
安全面试之XSS(跨站脚本攻击)
« 上一篇 07-24

发表评论

成为第一个评论的人

热门文章

标签TAG

最近回复