spring--4--spring之AutowiredAnnotationBeanPostProcessor源码

spring中注解方式的自动注入

1 项目xml配置

<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
       xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
       xmlns:context="http://www.springframework.org/schema/context"
       xsi:schemaLocation="http://www.springframework.org/schema/beans
                           http://www.springframework.org/schema/beans/spring-beans.xsd
                           http://www.springframework.org/schema/context
                           http://www.springframework.org/schema/context/spring-context.xsd">

    <!--开启包扫描,实际上
    BeanDefinitionReader在解析到这个标签的时候会自动向容器中添加5个固定的BeanDefinition
    (1)beanName internalConfigurationAnnotationProcessor 
        与之对应的类 ConfigurationClassPostProcessor
    (2)beanName internalEventListenerProcessor
     	与之对应的类 EventListenerMethodProcessor
    (3)beanName internalEventListenerFactory
  		与之对应的类 DefaultEventListenerFactory
    (4)beanName internalAutowiredAnnotationProcessor
  		与之对应的类 AutowiredAnnotationBeanPostProcessor
    (5)beanName internalCommonAnnotationProcessor
  		与之对应的类 CommonAnnotationBeanPostProcessor
    -->
    <context:component-scan base-package="cn"></context:component-scan>

    <!--在user属性上加入@Autowired注解-->
    <bean id="person" class="cn.lx.spring.v1.Person"></bean>

    <bean id="user" class="cn.lx.spring.v1.User">
        <property name="age" value="12"></property>
        <property name="name" value="LX"></property>
    </bean>

</beans>

要使用注解,那就必须开启包扫描

2 一些基本类

User

public class User {

    private String name;
    private String password;
    private int age;

    public User() {
    }

    public User(String name, String password) {
        this.name = name;
        this.password = password;
    }

    @Override
    public String toString() {
        return "User{" +
                "name='" + name + '\'' +
                ", password='" + password + '\'' +
                ", age=" + age +
                '}';
    }

    public String getName() {
        return name;
    }


    public void setName(String name) {
        this.name = name;
    }

    public String getPassword() {
        return password;
    }

    public void setPassword(String password) {
        this.password = password;
    }

    public int getAge() {
        return age;
    }

    public void setAge(int age) {
        this.age = age;
    }
}

Person

public class Person {

    @Autowired
    private User user;

    @Autowired
    private List<User> users;

    @Value("${java.version}")
    private String type;

    public Person() {
    }

    public Person(User user) {
        this.user = user;
    }

    @Autowired
    public User test(User user){
        System.out.println(user);
        return user;
    }


    public String getType() {
        return type;
    }

    public void setType(String type) {
        this.type = type;
    }

    public User getUser() {
        return user;
    }

    public void setUser(User user) {
        this.user = user;
    }

    public List<User> getUsers() {
        return users;
    }

    public void setUsers(List<User> users) {
        this.users = users;
    }

    @Override
    public String toString() {
        return "Person{" +
                "user=" + user +
                ", users=" + users +
                ", type='" + type + '\'' +
                '}';
    }
}

启动入口

public static void main(String[] args) {
    //声明一个可以读取xml配置文件的容器
    ClassPathXmlApplicationContext classPathXmlApplicationContext=new
            ClassPathXmlApplicationContext();

    //设置配置文件
    classPathXmlApplicationContext.setConfigLocation("spring-context.xml");

    //刷新容器,这是spring中最重要的方法,看懂了这个方法,bean的生命周期也就懂了
    classPathXmlApplicationContext.refresh();

    Person person = (Person) classPathXmlApplicationContext.getBean("person");
 
    System.out.println(person);

}

启动项目,观察控制台日志打印

15:24:34.384 [main] DEBUG org.springframework.beans.factory.xml.XmlBeanDefinitionReader - Loaded 7 bean definitions from class path resource [spring-context.xml]
15:24:34.432 [main] DEBUG org.springframework.beans.factory.support.DefaultListableBeanFactory - Creating shared instance of singleton bean 'org.springframework.context.annotation.internalConfigurationAnnotationProcessor'
15:24:34.482 [main] DEBUG org.springframework.beans.factory.support.DefaultListableBeanFactory - Creating shared instance of singleton bean 'org.springframework.context.event.internalEventListenerProcessor'
15:24:34.485 [main] DEBUG org.springframework.beans.factory.support.DefaultListableBeanFactory - Creating shared instance of singleton bean 'org.springframework.context.event.internalEventListenerFactory'
15:24:34.488 [main] DEBUG org.springframework.beans.factory.support.DefaultListableBeanFactory - Creating shared instance of singleton bean 'org.springframework.context.annotation.internalAutowiredAnnotationProcessor'
15:24:34.491 [main] DEBUG org.springframework.beans.factory.support.DefaultListableBeanFactory - Creating shared instance of singleton bean 'org.springframework.context.annotation.internalCommonAnnotationProcessor'
15:24:34.501 [main] DEBUG org.springframework.beans.factory.support.DefaultListableBeanFactory - Creating shared instance of singleton bean 'person'
15:24:34.558 [main] DEBUG org.springframework.beans.factory.support.DefaultListableBeanFactory - Creating shared instance of singleton bean 'user'
User{name='LX', password='null', age=12}
Person{user=User{name='LX', password='null', age=12}, users=[User{name='lx', password='null', age=12}], type='null'}

Process finished with exit code 0

上面日志说的很清楚,容器一共创建了7个bean对象,那么除了我们自己配置的两个bean对象外,另外的5个就只能是包扫描标签被解析的时候容器自动注册进去的。

3 @Autowired加在属性或普通方法上的自动注入原理

@Autowired注解自动注入是由AutowiredAnnotationBeanPostProcessor这个BeanPostProcessor完成的

直接找到这个类的源码,查看他的类图

在这里插入图片描述

结合@Autowired所拥有的功能,可以得到以下几点

(1) AutowiredAnnotationBeanPostProcessor间接实现了SmartInstantiationAwareBeanPostProcessor这个接口,这个接口有一个重要的方法determineCandidateConstructors,该方法可以在bean实例化的时候返回候选的构造函数,让spring使用这个构造函数实例化对象,所以@Autowired加载构造方法上可以干预实例化

(2) AutowiredAnnotationBeanPostProcessor间接实现了InstantiationAwareBeanPostProcessor这个接口,这个接口方法执行时机我们都知道

postProcessBeforeInstantiation 实例化前(主要是为了返回代理对象)

postProcessAfterInstantiation 属性赋值前

postProcessProperties 属性赋值前(postProcessAfterInstantiation方法之后)

(3)AutowiredAnnotationBeanPostProcessor实现了MergedBeanDefinitionPostProcessor接口,该接口的postProcessMergedBeanDefinition方法会在bean实例化后进行调用。

经过以上分析,我们得先看MergedBeanDefinitionPostProcessor接口的方法

public void postProcessMergedBeanDefinition(RootBeanDefinition beanDefinition, Class<?> beanType, String beanName) {
    //3.1查找类中的@Autowired和@Value注解,获取注入元数据
    InjectionMetadata metadata = findAutowiringMetadata(beanName, beanType, null);
    //3.2将需要自动注入的属性记录到BeanDefinition中
    metadata.checkConfigMembers(beanDefinition);
}

自动注入发生在属性赋值阶段,我们直接定位到属性赋值方法

/**
 * Populate the bean instance in the given BeanWrapper with the property values
 * from the bean definition.
 * @param beanName the name of the bean
 * @param mbd the bean definition for the bean
 * @param bw the BeanWrapper with bean instance
 */
@SuppressWarnings("deprecation")  // for postProcessPropertyValues
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.
    //InstantiationAwareBeanPostProcessor可以修改实例的属性,不过值有可能会被下面两种自动注入覆盖
    if (!mbd.isSynthetic() && hasInstantiationAwareBeanPostProcessors()) {
        for (BeanPostProcessor bp : getBeanPostProcessors()) {
            if (bp instanceof InstantiationAwareBeanPostProcessor) {
                InstantiationAwareBeanPostProcessor ibp = (InstantiationAwareBeanPostProcessor) bp;
                if (!ibp.postProcessAfterInstantiation(bw.getWrappedInstance(), beanName)) {
                    return;
                }
            }
        }
    }

    /************************************************************************************/      //非注解方式自动注入
    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和@Value注解属性自动注入
                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;
            }
        }
    }

/**************************************依赖检查***************************************/    
    if (needsDepCheck) {
        if (filteredPds == null) {
            filteredPds = filterPropertyDescriptorsForDependencyCheck(bw, mbd.allowCaching);
        }
        checkDependencies(beanName, mbd, filteredPds, pvs);
    }

    //统一设置属性
    if (pvs != null) {
        applyPropertyValues(beanName, mbd, bw, pvs);
    }
}

完成@Autowired和@Value注解属性自动注入

进入AutowiredAnnotationBeanPostProcessorpostProcessProperties方法

public PropertyValues postProcessProperties(PropertyValues pvs, Object bean, String beanName) {
    //3.1查找类中的@Autowired和@Value注解,获取注入元数据
    InjectionMetadata metadata = findAutowiringMetadata(beanName, bean.getClass(), pvs);
    try {
        //3.3注入属性
        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;
}

3.1查找类中的@Autowired和@Value注解,获取注入元数据

/**
 * @param beanName bean的名字
 * @param clazz bean的class对象
 * @param pvs 需要被赋值的属性集合
 */
private InjectionMetadata findAutowiringMetadata(String beanName, Class<?> clazz, @Nullable PropertyValues pvs) {
    // Fall back to class name as cache key, for backwards compatibility with custom callers.
    String cacheKey = (StringUtils.hasLength(beanName) ? beanName : clazz.getName());
    // Quick check on the concurrent map first, with minimal locking.
    //获取缓存中对应的注入元数据
    InjectionMetadata metadata = this.injectionMetadataCache.get(cacheKey);
    //注入元数据是否需要刷新(判断clazz是否相同)
    if (InjectionMetadata.needsRefresh(metadata, clazz)) {
        synchronized (this.injectionMetadataCache) {
            metadata = this.injectionMetadataCache.get(cacheKey);
            if (InjectionMetadata.needsRefresh(metadata, clazz)) {
                if (metadata != null) {
                    metadata.clear(pvs);
                }
                //解析clazz,获取类中的注入元数据
                metadata = buildAutowiringMetadata(clazz);
                //将该类的注入元数据缓存缓存
                this.injectionMetadataCache.put(cacheKey, metadata);
            }
        }
    }
    return metadata;
}

解析clazz,获取类中的注入元数据

private InjectionMetadata buildAutowiringMetadata(final Class<?> clazz) {
    /**
     * AutowiredAnnotationBeanPostProcessor默认构造方法会添加两个注解类到集合中
     * this.autowiredAnnotationTypes.add(Autowired.class);
	 * this.autowiredAnnotationTypes.add(Value.class);
	 * 这个方法的作用就是判断类中有没有携带这两个注解
	 * 没有直接返回空
     */
    if (!AnnotationUtils.isCandidateClass(clazz, this.autowiredAnnotationTypes)) {
        //表示一个空的注入元数据
        return InjectionMetadata.EMPTY;
    }

    List<InjectionMetadata.InjectedElement> elements = new ArrayList<>();
    Class<?> targetClass = clazz;

    do {
        final List<InjectionMetadata.InjectedElement> currElements = new ArrayList<>();
        
/************************************属性上的注解***************************************/
       
        //(1)遍历targetClass类的属性,回调接口方法
        ReflectionUtils.doWithLocalFields(targetClass, field -> {
            //(2)获取属性上的注解信息
            MergedAnnotation<?> ann = findAutowiredAnnotation(field);
            if (ann != null) {
                //静态属性
                if (Modifier.isStatic(field.getModifiers())) {
                    if (logger.isInfoEnabled()) {
                        logger.info("Autowired annotation is not supported on static fields: " + field);
                    }
                    return;
                }
                //(3)判断注解中required属性是否为true,没有该属性(@Value)直接false
                boolean required = determineRequiredStatus(ann);
                //将当前解析的注解信息添加到缓存中
                currElements.add(new AutowiredFieldElement(field, required));
            }
        });
/************************************方法上的注解***************************************/
        
         //(4)遍历targetClass类的方法,回调接口方法
        ReflectionUtils.doWithLocalMethods(targetClass, method -> {
            //获取方法对应的桥接方法(jvm相关知识点)
            Method bridgedMethod = BridgeMethodResolver.findBridgedMethod(method);
            if (!BridgeMethodResolver.isVisibilityBridgeMethodPair(method, bridgedMethod)) {
                return;
            }
            //获取方法上的注解,和获取属性上的注解方法一模一样
            MergedAnnotation<?> ann = findAutowiredAnnotation(bridgedMethod);
            //getMostSpecificMethod 将指定类接口方法对象转化为指定类的方法对象
            if (ann != null && method.equals(ClassUtils.getMostSpecificMethod(method, clazz))) {
                if (Modifier.isStatic(method.getModifiers())) {
                    if (logger.isInfoEnabled()) {
                        logger.info("Autowired annotation is not supported on static methods: " + method);
                    }
                    return;
                }
                //标注在方法上,方法必须有参数
                if (method.getParameterCount() == 0) {
                    if (logger.isInfoEnabled()) {
                        logger.info("Autowired annotation should only be used on methods with parameters: " +
                                    method);
                    }
                }
                //获取注解required属性的值
                boolean required = determineRequiredStatus(ann);
                //(5)找到当前方法的对应属性描述(解决@Autowired标注在get,set方法上)
                PropertyDescriptor pd = BeanUtils.findPropertyForMethod(bridgedMethod, clazz);
                //缓存
                currElements.add(new AutowiredMethodElement(method, required, pd));
            }
        });

        elements.addAll(0, currElements);
        //获取父类
        targetClass = targetClass.getSuperclass();
    }
    //它还要对父类里面的属性和方法在判断一次,一直到最顶层Object类
    while (targetClass != null && targetClass != Object.class);

    //(6)根据注解信息构建注入元数据
    return InjectionMetadata.forElements(elements, clazz);
}
(1)遍历targetClass类的属性,回调接口方法
/**
 * Invoke the given callback on all locally declared fields in the given class.
 * @param clazz the target class to analyze
 * @param fc the callback to invoke for each field
 * @throws IllegalStateException if introspection fails
 * @since 4.2
 * @see #doWithFields
 */
public static void doWithLocalFields(Class<?> clazz, FieldCallback fc) {
    //遍历属性
    for (Field field : getDeclaredFields(clazz)) {
        try {
            //回调接口方法
            fc.doWith(field);
        }
        catch (IllegalAccessException ex) {
            throw new IllegalStateException("Not allowed to access field '" + field.getName() + "': " + ex);
        }
    }
}
(2)获取属性上的注解信息
private MergedAnnotation<?> findAutowiredAnnotation(AccessibleObject ao) {
    //获取该属性的注解数据
    MergedAnnotations annotations = MergedAnnotations.from(ao);
    //遍历,判断该属性上的注解到底是哪一个(@Autowired,@Value)
    for (Class<? extends Annotation> type : this.autowiredAnnotationTypes) {
        MergedAnnotation<?> annotation = annotations.get(type);
        if (annotation.isPresent()) {
            return annotation;
        }
    }
    //无注解,返回null
    return null;
}
(3)获取注解中required属性值
/**
 * Determine if the annotated field or method requires its dependency.
 * <p>A 'required' dependency means that autowiring should fail when no beans
 * are found. Otherwise, the autowiring process will simply bypass the field
 * or method when no beans are found.
 * @param ann the Autowired annotation
 * @return whether the annotation indicates that a dependency is required
 */
@SuppressWarnings({"deprecation", "cast"})
protected boolean determineRequiredStatus(MergedAnnotation<?> ann) {
    // The following (AnnotationAttributes) cast is required on JDK 9+.
    return determineRequiredStatus((AnnotationAttributes)
                                   ann.asMap(mergedAnnotation -> new AnnotationAttributes(mergedAnnotation.getType())));
}


/**
 * Determine if the annotated field or method requires its dependency.
 * <p>A 'required' dependency means that autowiring should fail when no beans
 * are found. Otherwise, the autowiring process will simply bypass the field
 * or method when no beans are found.
 * @param ann the Autowired annotation
 * @return whether the annotation indicates that a dependency is required
 * @deprecated since 5.2, in favor of {@link #determineRequiredStatus(MergedAnnotation)}
 * 该方法已过时,jdk9以后不再使用该方法
 */
@Deprecated
protected boolean determineRequiredStatus(AnnotationAttributes ann) {
    //包含该属性,且属性为true时返回true,否则false
    return (!ann.containsKey(this.requiredParameterName) ||
            this.requiredParameterValue == ann.getBoolean(this.requiredParameterName));
}
(4)遍历targetClass类的方法,回调接口方法
/**
 * Perform the given callback operation on all matching methods of the given
 * class, as locally declared or equivalent thereof (such as default methods
 * on Java 8 based interfaces that the given class implements).
 * @param clazz the class to introspect
 * @param mc the callback to invoke for each method
 * @throws IllegalStateException if introspection fails
 * @since 4.2
 * @see #doWithMethods
 */
public static void doWithLocalMethods(Class<?> clazz, MethodCallback mc) {
    //遍历所有方法
    Method[] methods = getDeclaredMethods(clazz, false);
    for (Method method : methods) {
        try {
            //回调接口方法
            mc.doWith(method);
        }
        catch (IllegalAccessException ex) {
            throw new IllegalStateException("Not allowed to access method '" + method.getName() + "': " + ex);
        }
    }
}
(5)找到当前方法的对应属性描述(解决@Autowired标注在get,set方法上)

实际上就是判断当前方法是不是该类属性对应的set,get方法,如果是,那么就返回这个属性描述,交由处理属性注入的那个分支处理,否则就null,交由处理方法参数注入的那个分支。

/**
 * Find a JavaBeans {@code PropertyDescriptor} for the given method,
 * with the method either being the read method or the write method for
 * that bean property.
 * @param method the method to find a corresponding PropertyDescriptor for
 * @param clazz the (most specific) class to introspect for descriptors
 * @return the corresponding PropertyDescriptor, or {@code null} if none
 * @throws BeansException if PropertyDescriptor lookup fails
 * @since 3.2.13
 */
@Nullable
public static PropertyDescriptor findPropertyForMethod(Method method, Class<?> clazz) throws BeansException {
    Assert.notNull(method, "Method must not be null");
    //获取该类的所有属性描述
    PropertyDescriptor[] pds = getPropertyDescriptors(clazz);
    for (PropertyDescriptor pd : pds) {
        //当前方法是不是该属性的get或set方法
        if (method.equals(pd.getReadMethod()) || method.equals(pd.getWriteMethod())) {
            return pd;
        }
    }
    return null;
}
(6)根据注解信息构建注入元数据
/**
 * Return an {@code InjectionMetadata} instance, possibly for empty elements.
 * @param elements the elements to inject (possibly empty)
 * @param clazz the target class
 * @return a new {@link #InjectionMetadata(Class, Collection)} instance,
 * or {@link #EMPTY} in case of no elements
 * @since 5.2
 */
public static InjectionMetadata forElements(Collection<InjectedElement> elements, Class<?> clazz) {
    //构建注入元数据
    return (elements.isEmpty() ? new InjectionMetadata(clazz, Collections.emptyList()) :
            new InjectionMetadata(clazz, elements));
}

3.2将需要自动注入的属性记录到BeanDefinition中

public void checkConfigMembers(RootBeanDefinition beanDefinition) {
    Set<InjectedElement> checkedElements = new LinkedHashSet<>(this.injectedElements.size());
    for (InjectedElement element : this.injectedElements) {
        //获取被注入元素的属性对象
        Member member = element.getMember();
        //未记录就记录进去
        if (!beanDefinition.isExternallyManagedConfigMember(member)) {
            beanDefinition.registerExternallyManagedConfigMember(member);
            checkedElements.add(element);
        }
    }
    this.checkedElements = checkedElements;
}

3.3注入属性

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) {
          //注入(很明显的多态)
         element.inject(target, beanName, pvs);
      }
   }
}

注入

InjectedElement有两种类型(属性AutowiredFieldElement,方法参数AutowiredMethodElement),它们处理流程是不一样的。

(1)处理属性注入
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);
    }
    //未缓存,从BeanFactory中获取
    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 {
            //(3)BeanFactory根据依赖描述去获取容器中的对应的对象(关键方法)
            value = beanFactory.resolveDependency(desc, beanName, autowiredBeanNames, typeConverter);
        }
        catch (BeansException ex) {
            throw new UnsatisfiedDependencyException(null, beanName, new InjectionPoint(field), ex);
        }
        synchronized (this) {
            //未缓存,开始缓存
            if (!this.cached) {
                Object cachedFieldValue = null;
                if (value != null || this.required) {
                    cachedFieldValue = desc;
                    //将bean之间的依赖关系注册到工厂中
                    registerDependentBeans(beanName, autowiredBeanNames);
                    if (autowiredBeanNames.size() == 1) {
                        String autowiredBeanName = autowiredBeanNames.iterator().next();
                        if (beanFactory.containsBean(autowiredBeanName) &&
                            beanFactory.isTypeMatch(autowiredBeanName, field.getType())) {
                            cachedFieldValue = new ShortcutDependencyDescriptor(
                                desc, autowiredBeanName, field.getType());
                        }
                    }
                }
                this.cachedFieldValue = cachedFieldValue;
                this.cached = true;
            }
        } 
    }
    
    //反射,强行设置属性值(无论有没有set方法)
    if (value != null) {
        ReflectionUtils.makeAccessible(field);
        field.set(bean, value);
    }
}
(2)处理方法参数注入
protected void inject(Object bean, @Nullable String beanName, @Nullable PropertyValues pvs) throws Throwable {
    /**
     * 判断是否已经手动给该属性赋值,如果是,就直接跳过
     */
   if (checkPropertySkipping(pvs)) {
      return;
   }
   Method method = (Method) this.member;
   Object[] arguments;
   if (this.cached) {
      // Shortcut for avoiding synchronization...
      arguments = resolveCachedArguments(beanName);
   }
   else {
       //获取方法的参数数量
      int argumentCount = method.getParameterCount();
      arguments = new Object[argumentCount];
      DependencyDescriptor[] descriptors = new DependencyDescriptor[argumentCount];
      Set<String> autowiredBeans = new LinkedHashSet<>(argumentCount);
      Assert.state(beanFactory != null, "No BeanFactory available");
      TypeConverter typeConverter = beanFactory.getTypeConverter();
      for (int i = 0; i < arguments.length; i++) {
          //MethodParameter 封装方法参数的帮助类,它的构造方法还可以传入一个参数表示方法的第几个参数
         MethodParameter methodParam = new MethodParameter(method, i);
         DependencyDescriptor currDesc = new DependencyDescriptor(methodParam, this.required);
         currDesc.setContainingClass(bean.getClass());
         descriptors[i] = currDesc;
         try {
             //(3)调用同样的方法解析依赖
            Object arg = beanFactory.resolveDependency(currDesc, beanName, autowiredBeans, typeConverter);
            if (arg == null && !this.required) {
               arguments = null;
               break;
            }
            arguments[i] = arg;
         }
         catch (BeansException ex) {
            throw new UnsatisfiedDependencyException(null, beanName, new InjectionPoint(methodParam), ex);
         }
      }
      synchronized (this) {
          //缓存
         if (!this.cached) {
            if (arguments != null) {
               DependencyDescriptor[] cachedMethodArguments = Arrays.copyOf(descriptors, arguments.length);
               //将bean之间的依赖关系注册到工厂中
               registerDependentBeans(beanName, autowiredBeans);
               if (autowiredBeans.size() == argumentCount) {
                  Iterator<String> it = autowiredBeans.iterator();
                  Class<?>[] paramTypes = method.getParameterTypes();
                  for (int i = 0; i < paramTypes.length; i++) {
                     String autowiredBeanName = it.next();
                     if (beanFactory.containsBean(autowiredBeanName) &&
                           beanFactory.isTypeMatch(autowiredBeanName, paramTypes[i])) {
                        cachedMethodArguments[i] = new ShortcutDependencyDescriptor(
                              descriptors[i], autowiredBeanName, paramTypes[i]);
                     }
                  }
               }
               this.cachedMethodArguments = cachedMethodArguments;
            }
            else {
               this.cachedMethodArguments = null;
            }
            this.cached = true;
         }
      }
   }
    //反射执行有@Autowired注解的方法
   if (arguments != null) {
      try {
         ReflectionUtils.makeAccessible(method);
         method.invoke(bean, arguments);
      }
      catch (InvocationTargetException ex) {
         throw ex.getTargetException();
      }
   }
}
(3)解析依赖(关键方法)

BeanFactory根据依赖描述去获取容器中的对应的对象(关键方法)

这个方法在上一篇文章非注解ByType方式中已经粗略说过了。

在这里详细看一下这个方法

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

    /**
     * getParameterNameDiscoverer() 获取工厂中的ParameterNameDiscoverer用来解析方法参数名
     * initParameterNameDiscovery() 实际上就是将ParameterNameDiscoverer设置到依赖描述中
     * 在后面依赖描述会调用ParameterNameDiscoverer来解析方法参数名字
     */
   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 {
       //(3-1)属性懒加载注入
      Object result = getAutowireCandidateResolver().getLazyResolutionProxyIfNecessary(
            descriptor, requestingBeanName);
      if (result == null) {
          //(3-2)直接注入
         result = doResolveDependency(descriptor, requestingBeanName, autowiredBeanNames, typeConverter);
      }
      return result;
   }
}
(3-1)属性懒加载注入

这里就和非注解方式的自动注入不一样了,这里会判断在属性上是否添加了@Lazy注解,如果添加了,则返回一个代理对象,否则直接为null。

原本默认的AutowireCandidateResolver(自动注入的候选对象解析器)是SimpleAutowireCandidateResolver类型,但现在你在xml配置文件中配置<context:component-scan base-package="cn"></context:component-scan>表明你需要使用注解,这样XmlBeanDefinitionReader在解析到该标签的时候,会自动修改工厂中的AutowireCandidateResolver,将其更改为可以解析注解的ContextAnnotationAutowireCandidateResolver

public Object getLazyResolutionProxyIfNecessary(DependencyDescriptor descriptor, @Nullable String beanName) {
    //懒加载返回null,否则创建代理对象
   return (isLazy(descriptor) ? buildLazyResolutionProxy(descriptor, beanName) : null);
}

//判断是否懒加载
protected boolean isLazy(DependencyDescriptor descriptor) {
    
/***************************属性或者方法某个参数相关************************************/     
    //(3-1-1)获取所有注解信息(属性或者方法某个参数的)
   for (Annotation ann : descriptor.getAnnotations()) {
       //从当前注解中获取到@Lazy注解
      Lazy lazy = AnnotationUtils.getAnnotation(ann, Lazy.class);
       //value=true表示懒加载
      if (lazy != null && lazy.value()) {
         return true;
      }
   }
    
/********************************方法相关*****************************************/ 
    //获取方法参数对象
   MethodParameter methodParam = descriptor.getMethodParameter();
   if (methodParam != null) {
       //获取方法对象
      Method method = methodParam.getMethod();
      if (method == null || void.class == method.getReturnType()) {
          //MethodParam.getAnnotatedElement()其实就是返回方法对象
          //判断方法上面有没有标注@Lazy
          //getAnnotation这个方法是重载的
         Lazy lazy = AnnotationUtils.getAnnotation(methodParam.getAnnotatedElement(), Lazy.class);
         if (lazy != null && lazy.value()) {
            return true;
         }
      }
   }
   return false;
}
(3-1-1)获取所有注解信息
/**
 * Obtain the annotations associated with the wrapped field or method/constructor parameter.
 * 又分为两种情况
 */
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();
   }
}

属性

if (this.field != null) {
//第一次肯定是null
Annotation[] fieldAnnotations = this.fieldAnnotations;
if (fieldAnnotations == null) {
  //Field.getAnnotations()获取属性上的所有注解
  fieldAnnotations = this.field.getAnnotations();
  //缓存
  this.fieldAnnotations = fieldAnnotations;
}
return fieldAnnotations;
}

属性获取注解是非常简单的,这些简单的反射方法需要记住

方法参数

obtainMethodParameter()就是获取当前依赖描述中方法参数对象

/**
 * Return the wrapped MethodParameter, assuming it is present.
 * @return the MethodParameter (never {@code null})
 * @throws IllegalStateException if no MethodParameter is available
 * @since 5.0
 */
protected final MethodParameter obtainMethodParameter() {
   Assert.state(this.methodParameter != null, "Neither Field nor MethodParameter");
   return this.methodParameter;
}

调用MethodParametergetParameterAnnotations方法获取方法参数的全部注解信息

/**
 * Return the annotations associated with the specific method/constructor parameter.
 */
public Annotation[] getParameterAnnotations() {
   Annotation[] paramAnns = this.parameterAnnotations;
   if (paramAnns == null) {
       
       /**
        * Executable下边有两个子类Constructor,Method
        * 在这里this.executable中保存的就是方法对象
        * method.getParameterAnnotations()方法返回该方法参数的全部注解
        * 其中第一个[]代表该方法的第几个参数
        * 第二个[]代表这个参数的其中一个注解
        */
      Annotation[][] annotationArray = this.executable.getParameterAnnotations();
       //方法参数的索引
      int index = this.parameterIndex;
       //构造方法
      if (this.executable instanceof Constructor &&
            ClassUtils.isInnerClass(this.executable.getDeclaringClass()) &&
            annotationArray.length == this.executable.getParameterCount() - 1) {
         // Bug in javac in JDK <9: annotation array excludes enclosing instance parameter
         // for inner classes, so access it with the actual parameter index lowered by 1
         index = this.parameterIndex - 1;
      }
       
       /**
        * adaptAnnotationArray(annotationArray[index]) 
        * 这个方法没干啥,就是直接返回参数
        * annotationArray[index]是一个数组,表示当前索引位置方法参数的所有注解
        * Annotation[] EMPTY_ANNOTATION_ARRAY = new Annotation[0];
        */
      paramAnns = (index >= 0 && index < annotationArray.length ?
            adaptAnnotationArray(annotationArray[index]) : EMPTY_ANNOTATION_ARRAY);
       //缓存起来
      this.parameterAnnotations = paramAnns;
   }
   return paramAnns;
}
(3-2)直接注入
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;
        }

        //(3-2-1) 从依赖描述中获取依赖的类型
        Class<?> type = descriptor.getDependencyType();
        
/*****************************@Value注解处理*********************************/        
        //(3-2-2) 返回依赖描述中包含的value属性的值
        Object value = getAutowireCandidateResolver().getSuggestedValue(descriptor);    
        if (value != null) {
            if (value instanceof String) {
                //(3-2-3) 解析@Value注解
                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()));
            }
        }
/*****************************集合类型处理*********************************/  
         //(3-2-4) 解析需要注入多个bean的依赖描述(list,set集合这种情况)
        Object multipleBeans = resolveMultipleBeans(descriptor, beanName, autowiredBeanNames, typeConverter);
        if (multipleBeans != null) {
            return multipleBeans;
        }
        
/*****************************普通类型处理*********************************/         

        //根据type类型获取匹配的bean(见(3-2-4)
        Map<String, Object> matchingBeans = findAutowireCandidates(beanName, type, descriptor);
        if (matchingBeans.isEmpty()) {
            if (isRequired(descriptor)) {
                //required=true 必须注入对象,否则抛异常
                raiseNoMatchingBeanFound(type, descriptor.getResolvableType(), descriptor);
            }
            //required=false可以允许不注入
            return null;
        }

        String autowiredBeanName;
        Object instanceCandidate;

        //找到了多个类型匹配的bean
        if (matchingBeans.size() > 1) {
            //(3-2-5) 筛选出同时符合其他条件的bean(如果设置了的话)
            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);
        }
        
        //只有一个类型匹配的bean
        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);
        }
      
        //非注解方式,instanceCandidate才会是class
        if (instanceCandidate instanceof Class) {
            //getBean(autowiredBeanName)获取实例
            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);
    }
}
(3-2-1) 从依赖描述中获取依赖的类型
/**
 * Determine the declared (non-generic) type of the wrapped parameter/field.
 * @return the declared type (never {@code null})
 * 获取方法参数或属性的类型
 */
public Class<?> getDependencyType() {
    
/**************************************属性****************************************/    
    if (this.field != null) {
        if (this.nestingLevel > 1) {
            Type type = this.field.getGenericType();
            for (int i = 2; i <= this.nestingLevel; i++) {
                if (type instanceof ParameterizedType) {
                    Type[] args = ((ParameterizedType) type).getActualTypeArguments();
                    type = args[args.length - 1];
                }
            }
            if (type instanceof Class) {
                return (Class<?>) type;
            }
            else if (type instanceof ParameterizedType) {
                Type arg = ((ParameterizedType) type).getRawType();
                if (arg instanceof Class) {
                    return (Class<?>) arg;
                }
            }
            return Object.class;
        }
        else {
            //获取属性的最外层的类型
            return this.field.getType();
        }
    }
    
/**************************************方法参数****************************************/
    else {
        return obtainMethodParameter().getNestedParameterType();
    }
}

这个方法处理又是两个分支

属性

这个nestingLevel目前还不知道啥意思,就算是List<User>这种嵌套的,它也会return this.field.getType();返回List

方法参数

obtainMethodParameter()这个方法我们已经见过了,就是获取依赖描述中的方法参数对象。

主要看MethodParameter.getNestedParameterType()这个方法

/**
 * Return the nested type of the method/constructor parameter.
 * @return the parameter type (never {@code null})
 * @since 3.1
 * @see #getNestingLevel()
 */
public Class<?> getNestedParameterType() {
    
/**********************获取方法参数的嵌套类型*****************************/     
    /**
     * 首先你得明白nestingLevel这个属性代表的含义
     * 它表示的是嵌套的级别,默认为1
     * 举个例子,某个方法的参数是List<User> users类型的
     * 那么1就代表List,此时就返回List.class
     * 2代表User,此时就返回User.class
     */
    if (this.nestingLevel > 1) {
        Type type = getGenericParameterType();
        for (int i = 2; i <= this.nestingLevel; i++) {
            if (type instanceof ParameterizedType) {
                Type[] args = ((ParameterizedType) type).getActualTypeArguments();
                Integer index = getTypeIndexForLevel(i);
                type = args[index != null ? index : args.length - 1];
            }
            // TODO: Object.class if unresolvable
        }
        if (type instanceof Class) {
            return (Class<?>) type;
        }
        else if (type instanceof ParameterizedType) {
            Type arg = ((ParameterizedType) type).getRawType();
            if (arg instanceof Class) {
                return (Class<?>) arg;
            }
        }
        return Object.class;
    }
 /**********************获取方法参数的最外层类型*****************************/    
    else {
        return getParameterType();
    }
}


/**
 * Return the type of the method/constructor parameter.
 * @return the parameter type (never {@code null})
 */
public Class<?> getParameterType() {
    //首次肯定是null
    Class<?> paramType = this.parameterType;
    if (paramType != null) {
        return paramType;
    }
    if (getContainingClass() != getDeclaringClass()) {
        paramType = ResolvableType.forMethodParameter(this, null, 1).resolve();
    }
    if (paramType == null) {
        //获取方法参数类型其实很简单,先获取到方法对象,方法对象中就有方法参数类型
        paramType = computeParameterType();
    }
    //缓存
    this.parameterType = paramType;
    return paramType;
}

(3-2-2) 返回依赖描述中包含的@Value注解value属性的值
/**
 * Determine whether the given dependency declares a value annotation.
 * @see Value
 */
public Object getSuggestedValue(DependencyDescriptor descriptor) {
    //从属性和方法参数的所有注解中找到@Value注解value属性的值
    Object value = findValue(descriptor.getAnnotations());
    if (value == null) {
        MethodParameter methodParam = descriptor.getMethodParameter();
        if (methodParam != null) {
            //从属性和方法参数的所有注解中找到@Value注解value属性的值
            value = findValue(methodPaAram.getMethodAnnotations());
        }
    }
    return value;
}
(3-2-3) 解析@Value注解
public String resolveEmbeddedValue(@Nullable String value) {
    if (value == null) {
        return null;
    }
    String result = value;
    //遍历工厂中的值解析器,进行解析
    for (StringValueResolver resolver : this.embeddedValueResolvers) {
        result = resolver.resolveStringValue(result);
        if (result == null) {
            return null;
        }
    }
    return result;
}

spring在finishBeanFactoryInitialization方法中注册了一个和环境相关的值解析器

if (!beanFactory.hasEmbeddedValueResolver()) {
beanFactory.addEmbeddedValueResolver(strVal -> getEnvironment().resolvePlaceholders(strVal));
}
(3-2-4) 解析需要注入多个bean的依赖描述(list,set集合这种情况)
private Object resolveMultipleBeans(DependencyDescriptor descriptor, @Nullable String beanName,
                                    @Nullable Set<String> autowiredBeanNames, @Nullable TypeConverter typeConverter) {

    //获取依赖类型(见7.3(3-2-1))
    Class<?> type = descriptor.getDependencyType();

    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;
    }
    
/*********************************数组类型************************************/    
    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;
    }

/*******************************Collection集合并且是接口*******************************/
    else if (Collection.class.isAssignableFrom(type) && type.isInterface()) {
        //(1) 解析依赖描述,获取集合中元素的类型
        Class<?> elementType = descriptor.getResolvableType().asCollection().resolveGeneric();
        if (elementType == null) {
            return null;
        }
        
        //(2) 根据元素类型,获取匹配的bean
        Map<String, Object> matchingBeans = findAutowireCandidates(beanName, elementType,
                                                                   new MultiElementDescriptor(descriptor));
        if (matchingBeans.isEmpty()) {
            return null;
        }
        //将注入的bean的名字记录到工厂中
        if (autowiredBeanNames != null) {
            autowiredBeanNames.addAll(matchingBeans.keySet());
        }
        TypeConverter converter = (typeConverter != null ? typeConverter : getTypeConverter());
        //将map集合的values转化为type类型(type是Collection集合)
        Object result = converter.convertIfNecessary(matchingBeans.values(), type);
        //对list集合进行排序
        if (result instanceof List) {
            if (((List<?>) result).size() > 1) {
                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;
    }
}

(1) 解析依赖描述,获取集合中元素的类型

/**
 * Build a {@link ResolvableType} object for the wrapped parameter/field.
 * @since 4.0
 */
public ResolvableType getResolvableType() {
   ResolvableType resolvableType = this.resolvableType;
    //首次,解析
   if (resolvableType == null) {
       //根据类型构建对应的ResolvableType
      resolvableType = (this.field != null ?
            ResolvableType.forField(this.field, this.nestingLevel, this.containingClass) :
            ResolvableType.forMethodParameter(obtainMethodParameter()));
      this.resolvableType = resolvableType;
   }
   return resolvableType;
}

(2) 根据元素类型,获取匹配的bean

/**
 * Find bean instances that match the required type.
 * Called during autowiring for the specified bean.
 * @param beanName the name of the bean that is about to be wired
 * @param requiredType the actual type of bean to look for
 * (may be an array component type or collection element type)
 * @param descriptor the descriptor of the dependency to resolve
 * @return a Map of candidate names and candidate instances that match
 * the required type (never {@code null})
 * @throws BeansException in case of errors
 * @see #autowireByType
 * @see #autowireConstructor
 */
protected Map<String, Object> findAutowireCandidates(
    @Nullable String beanName, Class<?> requiredType, DependencyDescriptor descriptor) {

    //调用工具类的方法获取所有requiredType类型的bean的名字
    String[] candidateNames = BeanFactoryUtils.beanNamesForTypeIncludingAncestors(
        this, requiredType, true, descriptor.isEager());
    
     /**
      * this.resolvableDependencies 有4个对象,都是容器内部对象
      * ApplicationEventPublisher
      * ResourceLoader
      * ApplicationContext
      * BeanFactory
      * 这4中类型的属性在此处可以自动注入
      */
    Map<String, Object> result = new LinkedHashMap<>(candidateNames.length);
    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) {
        /**
         * !isSelfReference(beanName, candidate) 
         * 非自身引用(candidate是beanName的FactoryBean这种情况也算自身引用)
         *
         * isAutowireCandidate(candidate, descriptor)
         * 判断candidate是否可以作为自动注入候选
         */
        if (!isSelfReference(beanName, candidate) && isAutowireCandidate(candidate, descriptor)) {
            //使用getBean(candidate)获取对应的实例,然后再以candidate为key放入result中
            //重点看一下这个方法
            addCandidateEntry(result, candidate, descriptor, requiredType);
        }
    }
    
    //说明此时candidate不满足候选条件,需要进行特殊处理
    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;
}

重点看一下addCandidateEntry这个方法

/**
 * Add an entry to the candidate map: a bean instance if available or just the resolved
 * type, preventing early bean initialization ahead of primary candidate selection.
 */
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已经实例化
   else if (containsSingleton(candidateName) || (descriptor instanceof StreamDependencyDescriptor &&
         ((StreamDependencyDescriptor) descriptor).isOrdered())) {
       //resolveCandidate方法中调用getBean(beanName)获取实例
      Object beanInstance = descriptor.resolveCandidate(candidateName, requiredType, this);
      candidates.put(candidateName, (beanInstance instanceof NullBean ? null : beanInstance));
   }
    
   //candidateName未实例化
   else {
       //此处getType不是实例化,而是获取candidateName对应类型的class对象
      candidates.put(candidateName, getType(candidateName));
   }
}
(3-2-5) 筛选出同时符合其他条件的bean(如果设置了的话)
/**
 * Determine the autowire candidate in the given set of beans.
 * <p>Looks for {@code @Primary} and {@code @Priority} (in that order).
 * @param candidates a Map of candidate names and candidate instances
 * that match the required type, as returned by {@link #findAutowireCandidates}
 * @param descriptor the target dependency to match against
 * @return the name of the autowire candidate, or {@code null} if none found
 */
@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;
    }
    
    //有@Priority注解或实现了Priority接口的优先级最高的
    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;
}

determineAutowireCandidate方法,总结如下:

@Autowired并不单是按类型进行注入,当匹配到多个bean的时候,会遵循如下原则进行筛选

(1)有@Primary注解的

(2)有@Priority注解或实现了Priority接口的优先级最高的

(3)不满足上面两种就按名字匹配bean

4 @Autowired加在构造方法上的自动注入原理

@Autowired注解加在构造方法上,就表明需要使用该构造方实例化对象。AutowiredAnnotationBeanPostProcessor间接实现了SmartInstantiationAwareBeanPostProcessor这个接口,这个接口有一个重要的方法determineCandidateConstructors,这个方法执行完会返回有@Autowired注解的构造方法(如果required=false,那么返回的构造方法不止一个),然后调用autowireConstructor(beanName, mbd, ctors, args)这个方法筛选出最优的构造方法执行自动注入,然后实例化。

下面是spring中bean实例化方法的源码

/**
 * Create a new instance for the specified bean, using an appropriate instantiation strategy:
 * factory method, constructor autowiring, or simple instantiation.
 * @param beanName the name of the bean
 * @param mbd the bean definition for the bean
 * @param args explicit arguments to use for constructor or factory method invocation
 * @return a BeanWrapper for the new instance
 * @see #obtainFromSupplier
 * @see #instantiateUsingFactoryMethod
 * @see #autowireConstructor
 * @see #instantiateBean
 */
protected BeanWrapper createBeanInstance(String beanName, RootBeanDefinition mbd, @Nullable Object[] args) {
    // Make sure bean class is actually resolved at this point.
    //获取需要实例化的bean的类型
    Class<?> beanClass = resolveBeanClass(mbd, beanName);

    if (beanClass != null && !Modifier.isPublic(beanClass.getModifiers()) && !mbd.isNonPublicAccessAllowed()) {
        throw new BeanCreationException(mbd.getResourceDescription(), beanName,
                                        "Bean class isn't public, and non-public access not allowed: " + beanClass.getName());
    }

    Supplier<?> instanceSupplier = mbd.getInstanceSupplier();
    if (instanceSupplier != null) {
        return obtainFromSupplier(instanceSupplier, beanName);
    }

    //工厂方法实例化对象
    if (mbd.getFactoryMethodName() != null) {
        return instantiateUsingFactoryMethod(beanName, mbd, args);
    }

    // Shortcut when re-creating the same bean...
    //重新创建对象的快捷方式
    boolean resolved = false;
    boolean autowireNecessary = false;
    if (args == null) {
        synchronized (mbd.constructorArgumentLock) {
            if (mbd.resolvedConstructorOrFactoryMethod != null) {
                resolved = true;
                autowireNecessary = mbd.constructorArgumentsResolved;
            }
        }
    }
    if (resolved) {
        if (autowireNecessary) {
            return autowireConstructor(beanName, mbd, null, null);
        }
        else {
            return instantiateBean(beanName, mbd);
        }
    }
/********************************构造方法自动注入*******************************/
    // Candidate constructors for autowiring?
    //4.1返回@Autowired注解标注的构造方法
    Constructor<?>[] ctors = determineConstructorsFromBeanPostProcessors(beanClass, beanName);
    /**
     * ctors != null 说明有@Autowired注解标注的构造方法,此时会执行autowireConstructor方法
     * 从ctors中再挑出一个合适的构造方法进行实例化
     */
    if (ctors != null || mbd.getResolvedAutowireMode() == AUTOWIRE_CONSTRUCTOR ||
        mbd.hasConstructorArgumentValues() || !ObjectUtils.isEmpty(args)) {
        //4.2进一步选择合适的constructor实例化对象
        return autowireConstructor(beanName, mbd, ctors, args);
    }

    // Preferred constructors for default construction?
    //获取首选的默认构造方法
    ctors = mbd.getPreferredConstructors();
    if (ctors != null) {
        return autowireConstructor(beanName, mbd, ctors, null);
    }

    // No special handling: simply use no-arg constructor.
    //使用无参构造方法
    return instantiateBean(beanName, mbd);
}

4.1获取@Autowired注解标注的构造方法

public Constructor<?>[] determineCandidateConstructors(Class<?> beanClass, final String beanName)
    throws BeanCreationException {
    
/********************************处理@Lookup注解***********************************/
    // Let's check for lookup methods here...
    if (!this.lookupMethodsChecked.contains(beanName)) {
        if (AnnotationUtils.isCandidateClass(beanClass, Lookup.class)) {
            try {
                Class<?> targetClass = beanClass;
                do {
                    ReflectionUtils.doWithLocalMethods(targetClass, method -> {
                        Lookup lookup = method.getAnnotation(Lookup.class);
                        if (lookup != null) {
                            Assert.state(this.beanFactory != null, "No BeanFactory available");
                            LookupOverride override = new LookupOverride(method, lookup.value());
                            try {
                                //获取对应beanName的BeanDefinition
                                RootBeanDefinition mbd = (RootBeanDefinition)
                                    this.beanFactory.getMergedBeanDefinition(beanName);
                                //将当前lookup注解标注的方法添加到方法重写列表中
                                mbd.getMethodOverrides().addOverride(override);
                            }
                            catch (NoSuchBeanDefinitionException ex) {
                                throw new BeanCreationException(beanName,
                                                                "Cannot apply @Lookup to beans without corresponding bean definition");
                            }
                        }
                    });
                    targetClass = targetClass.getSuperclass();
                }
                while (targetClass != null && targetClass != Object.class);

            }
            catch (IllegalStateException ex) {
                throw new BeanCreationException(beanName, "Lookup method resolution failed", ex);
            }
        }
        this.lookupMethodsChecked.add(beanName);
    }

/********************************处理@Autowired构造方法***********************************/
    // Quick check on the concurrent map first, with minimal locking.
    //获取缓存中的候选构造方法的列表
    Constructor<?>[] candidateConstructors = this.candidateConstructorsCache.get(beanClass);
    if (candidateConstructors == null) {
        // Fully synchronized resolution now...
        synchronized (this.candidateConstructorsCache) {
            candidateConstructors = this.candidateConstructorsCache.get(beanClass);
            if (candidateConstructors == null) {
                Constructor<?>[] rawCandidates;
                try {
                    //获取所有构造方法
                    rawCandidates = beanClass.getDeclaredConstructors();
                }
                catch (Throwable ex) {
                    throw new BeanCreationException(beanName,
                                                    "Resolution of declared constructors on bean Class [" + beanClass.getName() +
                                                    "] from ClassLoader [" + beanClass.getClassLoader() + "] failed", ex);
                }
                List<Constructor<?>> candidates = new ArrayList<>(rawCandidates.length);
                Constructor<?> requiredConstructor = null;
                Constructor<?> defaultConstructor = null;
                //获取主构造方法(Kotlin classes相关)
                Constructor<?> primaryConstructor = BeanUtils.findPrimaryConstructor(beanClass);
                int nonSyntheticConstructors = 0;
                //遍历构造方法
                for (Constructor<?> candidate : rawCandidates) {
                    //计数加一
                    if (!candidate.isSynthetic()) {
                        nonSyntheticConstructors++;
                    }
                    else if (primaryConstructor != null) {
                        continue;
                    }
                    //获取当前构造方法的@Autowired注解信息(见3.1(2))
                    MergedAnnotation<?> ann = findAutowiredAnnotation(candidate);
                    if (ann == null) {
                        //获取用户类(解决cglib生成的代理类这种情况)
                        Class<?> userClass = ClassUtils.getUserClass(beanClass);
                        if (userClass != beanClass) {
                            //获取用户类构造方法上的注解信息
                            try {
                                Constructor<?> superCtor =
                                    userClass.getDeclaredConstructor(candidate.getParameterTypes());
                                ann = findAutowiredAnnotation(superCtor);
                            }
                            catch (NoSuchMethodException ex) {
                                // Simply proceed, no equivalent superclass constructor found...
                            }
                        }
                    }
                    if (ann != null) {
                        //此时又来了一个构造方法标注了@Autowired注解,肯定抛异常啊
                        if (requiredConstructor != null) {
                            throw new BeanCreationException(beanName,
                                                            "Invalid autowire-marked constructor: " + candidate +
                                                            ". Found constructor with 'required' Autowired annotation already: " +
                                                            requiredConstructor);
                        }
                        //获取@Autowired注解中required属性的值
                        boolean required = determineRequiredStatus(ann);
                        //required属性为true的时候,只能存在一个有@Autowired注解的构造方法
                        if (required) {
                            if (!candidates.isEmpty()) {
                                throw new BeanCreationException(beanName,
                                                                "Invalid autowire-marked constructors: " + candidates +
                                                                ". Found constructor with 'required' Autowired annotation: " +
                                                                candidate);
                            }
                            //当前构造方法是required构造方法
                            requiredConstructor = candidate;
                        }
                        //将有@Autowired注解的构造方法保存到candidates集合中
                        candidates.add(candidate);
                    }
                    //没有@Autowired注解,并且当前方法参数为0说明是默认构造方法
                    else if (candidate.getParameterCount() == 0) {
                        defaultConstructor = candidate;
                    }
                }
                
                
                if (!candidates.isEmpty()) {
                    //有加了@Autowired的构造方法
                    // Add default constructor to list of optional constructors, as fallback.
                    //required属性为false
                    if (requiredConstructor == null) {
                        //将默认构造方法添加到候选构造方法中
                        if (defaultConstructor != null) {
                            candidates.add(defaultConstructor);
                        }
                        //不存在默认构造方法,且只有一个构造方法加了@Autowired注解,打印一下日志信息
                        else if (candidates.size() == 1 && logger.isInfoEnabled()) {
                            logger.info("Inconsistent constructor declaration on bean with name '" + beanName +
                                        "': single autowire-marked constructor flagged as optional - " +
                                        "this constructor is effectively required since there is no " +
                                        "default constructor to fall back to: " + candidates.get(0));
                        }
                    }
                    //集合转数组
                    candidateConstructors = candidates.toArray(new Constructor<?>[0]);
                }
                //没有加@Autowired的构造方法,且只有一个构造方法,那么就使用当前构造方法
                else if (rawCandidates.length == 1 && rawCandidates[0].getParameterCount() > 0) {
                    candidateConstructors = new Constructor<?>[] {rawCandidates[0]};
                }
                //没有加@Autowired的构造方法,主构造方法(Kotlin classes相关)不为空,那么就使用primaryConstructor和默认构造方法
                else if (nonSyntheticConstructors == 2 && primaryConstructor != null &&
                         defaultConstructor != null && !primaryConstructor.equals(defaultConstructor)) {
                    candidateConstructors = new Constructor<?>[] {primaryConstructor, defaultConstructor};
                }
                //没有加@Autowired的构造方法,主构造方法(Kotlin classes相关)不为空,那么就使用primaryConstructor
                else if (nonSyntheticConstructors == 1 && primaryConstructor != null) {
                    candidateConstructors = new Constructor<?>[] {primaryConstructor};
                }
                //空的构造方法数组
                else {
                    candidateConstructors = new Constructor<?>[0];
                }
                //缓存当前解析过的构造方法
                this.candidateConstructorsCache.put(beanClass, candidateConstructors);
            }
        }
    }
    return (candidateConstructors.length > 0 ? candidateConstructors : null);
}

4.2进一步选择合适的constructor实例化对象

autowireConstructor(beanName, mbd, ctors, args);

这个方法在上一篇文章非注解方式自动注入中详细解释过,这里就不在赘述了。

  • 1
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值