Spring源码解析(七)-IOC的依赖注入

前面六章我们完成了IOC容器的初始化,那么这章我们来看看IOC的依赖注入。有二种情况会发生依赖注入:
1)用户第一次向IOC容器索要Bean时触发
2)在<Bean>元素中配置了lazy-init属性,让容器在解析注册Bean时触发
我们这里只对getBean方式进行分析

getBean触发依赖注入

我们以AbstractBeanFactory为例,分析其向容器索取的处理过程

AbstractBeanFactory的getBean相关方法的源码如下:
    @Override
    public Object getBean(String name) throws BeansException {
        return doGetBean(name, null, null, false);
    }

    @Override
    public <T> T getBean(String name, Class<T> requiredType) throws BeansException {
        return doGetBean(name, requiredType, null, false);
    }

    @Override
    public Object getBean(String name, Object... args) throws BeansException {
        return doGetBean(name, null, args, false);
    }

    public <T> T getBean(String name, Class<T> requiredType, Object... args) throws BeansException {
        return doGetBean(name, requiredType, args, false);
    }

具体实现

    //实际获取bean的地方,也是触发依赖注入发生的地方
    @SuppressWarnings("unchecked")
    protected <T> T doGetBean(
            final String name, final Class<T> requiredType, final Object[] args, boolean typeCheckOnly)
            throws BeansException {
        //bean name处理,去除带"&"name前缀。
        //若指定的是别名,则将别名转换为规范的Bean名称
        final String beanName = transformedBeanName(name);
        Object bean;

        // Eagerly check singleton cache for manually registered singletons.
        //从缓存中获取已经被创建过的单例模式的Bean,这种bean只创建一次,不重复创建  
        Object sharedInstance = getSingleton(beanName);
   
        if (sharedInstance != null && args == null) {
            if (logger.isDebugEnabled()) {
                if (isSingletonCurrentlyInCreation(beanName)) {
                    logger.debug("Returning eagerly cached instance of singleton bean '" + beanName +
                            "' that is not fully initialized yet - a consequence of a circular reference");
                }
                else {
                    logger.debug("Returning cached instance of singleton bean '" + beanName + "'");
                }
            }
            //获取给定Bean的实例对象,主要是完成FactoryBean的相关处理  
            bean = getObjectForBeanInstance(sharedInstance, name, beanName, null);
        }

        else {
            // Fail if we're already creating this bean instance:
            // We're assumably within a circular reference.
            //缓存中已经有已经创建的原型模式Bean,但是由于循环引用的问题导致实例化失败
            if (isPrototypeCurrentlyInCreation(beanName)) {
                throw new BeanCurrentlyInCreationException(beanName);
            }

            // Check if bean definition exists in this factory.
            //对IOC容器中是否存在BeanDefintion进行检查,检查能否在当前的BeanFactory容器中取到
            //需要的Bean。如果取不到,则到双亲BeanFactory中去取,如果双亲的Factory中也取不到,
            //就顺着双亲BeanFactory链一直向上查找
            BeanFactory parentBeanFactory = getParentBeanFactory();
            //父容器存在,且在当前容器中找不到指定的bean
            if (parentBeanFactory != null && !containsBeanDefinition(beanName)) {
                // Not found -> check parent.
                //还原"&"的name,委托父类按照不同的参数查找(递归)
                String nameToLookup = originalBeanName(name);
                if (args != null) {
                    // Delegation to parent with explicit args.
                    return (T) parentBeanFactory.getBean(nameToLookup, args);
                }
                else {
                    // No args -> delegate to standard getBean method.
                    return parentBeanFactory.getBean(nameToLookup, requiredType);
                }
            }
            //Bean是否需要进行类型验证
            if (!typeCheckOnly) {
                //将beanName放入名为alreadyCreated的Set集合中(做一个标识)
                markBeanAsCreated(beanName);
            }

            try {
                //根据beanName获取BeanDefinition,若存在父级bean,则合并父类公共属性问题
                final RootBeanDefinition mbd = getMergedLocalBeanDefinition(beanName);
                checkMergedBeanDefinition(mbd, beanName, args);

                // Guarantee initialization of beans that the current bean depends on.
                //获取当前Bean所有依赖Bean的名称 (递归)
                String[] dependsOn = mbd.getDependsOn();
                if (dependsOn != null) {
                    for (String dependsOnBean : dependsOn) {
                        //判断是否依赖的bean已经被注册
                        if (isDependent(beanName, dependsOnBean)) {
                            throw new BeanCreationException(mbd.getResourceDescription(), beanName,
                                    "Circular depends-on relationship between '" + beanName + "' and '" + dependsOnBean + "'");
                        }
                        //把被依赖Bean注册给当前依赖的Bean
                        registerDependentBean(dependsOnBean, beanName);
                        //递归获取当前bean的依赖bean
                        getBean(dependsOnBean);
                    }
                }

                // Create bean instance.
                //单态模式Bean
                if (mbd.isSingleton()) {
                    //匿名内部类
                    sharedInstance = getSingleton(beanName, new ObjectFactory<Object>() {
                        @Override
                        public Object getObject() throws BeansException {
                            try {
                                //创建一个指定Bean实例对象,在下面详解
                                return createBean(beanName, mbd, args);
                            }
                            catch (BeansException ex) {
                                //从容器单态模式Bean缓存中清除实例对象 
                                destroySingleton(beanName);
                                throw ex;
                            }
                        }
                    });
                    //获取给定Bean的实例对象
                    bean = getObjectForBeanInstance(sharedInstance, name, beanName, mbd);
                }
                //原型模式Bean
                else if (mbd.isPrototype()) {
                    // It's a prototype -> create a new instance.
                    Object prototypeInstance = null;
                    try {
                        //创建原型前的回调方法,主要是将beanName放到名为prototypesCurrentlyInCreation的ThreadLocal中
                        beforePrototypeCreation(beanName);
                        //创建一个指定Bean实例对象
                        prototypeInstance = createBean(beanName, mbd, args);
                    }
                    finally {
                        //创建原型后的回调方法,主要是将beanName从名为prototypesCurrentlyInCreation的ThreadLocal中移除
                        afterPrototypeCreation(beanName);
                    }
                    //获取给定Bean的实例对象
                    bean = getObjectForBeanInstance(prototypeInstance, name, beanName, mbd);
                }
                //创建的Bean既不是单态模式,也不是原型模式,如:request、session等生命周期
                //代码逻辑类似创建原型Bean
                else {
                    String scopeName = mbd.getScope();
                    final Scope scope = this.scopes.get(scopeName);
                    if (scope == null) {
                        throw new IllegalStateException("No Scope registered for scope name '" + scopeName + "'");
                    }
                    try {
                        Object scopedInstance = scope.get(beanName, new ObjectFactory<Object>() {
                            @Override
                            public Object getObject() throws BeansException {
                                beforePrototypeCreation(beanName);
                                try {
                                    return createBean(beanName, mbd, args);
                                }
                                finally {
                                    afterPrototypeCreation(beanName);
                                }
                            }
                        });
                        bean = getObjectForBeanInstance(scopedInstance, name, beanName, mbd);
                    }
                    catch (IllegalStateException ex) {
                        throw new BeanCreationException(beanName,
                                "Scope '" + scopeName + "' is not active for the current thread; consider " +
                                "defining a scoped proxy for this bean if you intend to refer to it from a singleton",
                                ex);
                    }
                }
            }
            catch (BeansException ex) {
                cleanupAfterBeanCreationFailure(beanName);
                throw ex;
            }
        }

        //对创建的Bean实例对象进行类型检查
        if (requiredType != null && bean != null && !requiredType.isAssignableFrom(bean.getClass())) {
            try {
                //将bean转化成指定的类型
                return getTypeConverter().convertIfNecessary(bean, requiredType);
            }
            catch (TypeMismatchException ex) {
                if (logger.isDebugEnabled()) {
                    logger.debug("Failed to convert bean '" + name + "' to required type [" +
                            ClassUtils.getQualifiedName(requiredType) + "]", ex);
                }
                throw new BeanNotOfRequiredTypeException(name, requiredType, bean.getClass());
            }
        }
        //返回Bean,这个Bean已经是包含了依赖关系的Bean
        return (T) bean;
    }

由上面的代码分析得知Bean有很多模式,单态,原型和其他类型。我们通常接触的是单态和原型。其中单态有缓存,用来提高效率。Spring默认不配置的使用单态模式。

下面我们来看看createBean方法

AbstractAutowireCapableBeanFactory类的createBean方法

    //创建Bean实例对象
    @Override
    protected Object createBean(final String beanName, final RootBeanDefinition mbd, final Object[] args)
            throws BeanCreationException {

        if (logger.isDebugEnabled()) {
            logger.debug("Creating instance of bean '" + beanName + "'");
        }
        //判断需要创建的Bean是否可以实例化,这个类是否可以通过类装载器载入
        resolveBeanClass(mbd, beanName);

        //校验和准备Bean中的方法覆盖
        try {
            mbd.prepareMethodOverrides();
        }
        catch (BeanDefinitionValidationException ex) {
            throw new BeanDefinitionStoreException(mbd.getResourceDescription(),
                    beanName, "Validation of method overrides failed", ex);
        }

        try {
            //如果Bean配置了PostProcessor,则返回Bean的代理对象
            Object bean = resolveBeforeInstantiation(beanName, mbd);
            if (bean != null) {
                return bean;
            }
        }
        catch (Throwable ex) {
            throw new BeanCreationException(mbd.getResourceDescription(), beanName,
                    "BeanPostProcessor before instantiation of bean failed", ex);
        }
     
        //真正创建Bean的入口 
        Object beanInstance = doCreateBean(beanName, mbd, args);
        if (logger.isDebugEnabled()) {
            logger.debug("Finished creating instance of bean '" + beanName + "'");
        }
        return beanInstance;
    }
   
     //这里其实也用到了模板设计模式,一般返回Bean的代理。这里不做详细介绍了
     //想要debug的朋友,只要声明一个beanPostProcessor实现InstantiationAwareBeanPostProcessor接口
     //然后再第2章的4行代码中加入factory.addBeanPostProcessor(beanPostProcessor);就可以就行调试了
     protected Object resolveBeforeInstantiation(String beanName, RootBeanDefinition mbd) {
        Object bean = null;
        if (!Boolean.FALSE.equals(mbd.beforeInstantiationResolved)) {
            // Make sure bean class is actually resolved at this point.
            if (!mbd.isSynthetic() && hasInstantiationAwareBeanPostProcessors()) {
                Class<?> targetType = determineTargetType(beanName, mbd);
                if (targetType != null) {
                    bean = applyBeanPostProcessorsBeforeInstantiation(targetType, beanName);
                    if (bean != null) {
                        bean = applyBeanPostProcessorsAfterInitialization(bean, beanName);
                    }
                }
            }
            mbd.beforeInstantiationResolved = (bean != null);
        }
        return bean;
    }

接下来我们来看一下具体的Bean是怎么生成的

    protected Object doCreateBean(final String beanName, final RootBeanDefinition mbd, final Object[] args) {
        //用来封装被创建的Bean对象
        BeanWrapper instanceWrapper = null;
        //单态模式的Bean
        if (mbd.isSingleton()) {
            //从缓存中获取同名BeanName并给instanceWrapper 赋值
            instanceWrapper = this.factoryBeanInstanceCache.remove(beanName);
        }
        if (instanceWrapper == null) {
            //创建实例对象,这个方法在下面做详细介绍
            instanceWrapper = createBeanInstance(beanName, mbd, args);
        }
        //获得代理的对象,如:com.test.spring.PersonImpl@d706f19
        final Object bean = (instanceWrapper != null ? instanceWrapper.getWrappedInstance() : null);
        //获取class对象,如:class  com.test.spring.PersonImpl
        Class<?> beanType = (instanceWrapper != null ? instanceWrapper.getWrappedClass() : null);

        // Allow post-processors to modify the merged bean definition.
        synchronized (mbd.postProcessingLock) {
            if (!mbd.postProcessed) {
                //如果BeanPostProcessor中存在MergedBeanDefinitionPostProcessor则对BeanDefinition做一些合并处理,其实就是后置处理器
                applyMergedBeanDefinitionPostProcessors(mbd, beanType, beanName);
                mbd.postProcessed = true;
            }
        }

        //向容器中缓存单态模式的Bean对象,以防循环引用
        boolean earlySingletonExposure = (mbd.isSingleton() && this.allowCircularReferences &&
                isSingletonCurrentlyInCreation(beanName));
        if (earlySingletonExposure) {
            if (logger.isDebugEnabled()) {
                logger.debug("Eagerly caching bean '" + beanName +
                        "' to allow for resolving potential circular references");
            }
            //匿名内部类,将对象放入缓存(Map,Set)中  
            addSingletonFactory(beanName, new ObjectFactory<Object>() {
                @Override
                public Object getObject() throws BeansException {
                    return getEarlyBeanReference(beanName, mbd, bean);
                }
            });
        }

        //bean的初始化
        Object exposedObject = bean;
        try {
            //将Bean实例对象封装,并且Bean定义中配置的属性值赋值给实例对象,后面详解
            populateBean(beanName, mbd, instanceWrapper);
            if (exposedObject != null) {
                //初始化Bean对象
                exposedObject = initializeBean(beanName, exposedObject, mbd);
            }
        }
        catch (Throwable ex) {
            if (ex instanceof BeanCreationException && beanName.equals(((BeanCreationException) ex).getBeanName())) {
                throw (BeanCreationException) ex;
            }
            else {
                throw new BeanCreationException(mbd.getResourceDescription(), beanName, "Initialization of bean failed", ex);
            }
        }

        if (earlySingletonExposure) {
            //获取已注册的单态模式Bean对象
            Object earlySingletonReference = getSingleton(beanName, false);
            if (earlySingletonReference != null) {
                //判断获取的已注册的Bean和正在实例化的Bean是否是同一个 
                if (exposedObject == bean) {
                    exposedObject = earlySingletonReference;
                }
                //当前Bean是否依赖其他Bean,并且当发生循环引用时不允许新创建实例对象  
                else if (!this.allowRawInjectionDespiteWrapping && hasDependentBean(beanName)) {
                    //获取当前Bean的依赖Bean  
                    String[] dependentBeans = getDependentBeans(beanName);
                    Set<String> actualDependentBeans = new LinkedHashSet<String>(dependentBeans.length);
                    for (String dependentBean : dependentBeans) {
                        //对依赖Bean进行类型检查 
                        if (!removeSingletonIfCreatedForTypeCheckOnly(dependentBean)) {
                            actualDependentBeans.add(dependentBean);
                        }
                    }
                    if (!actualDependentBeans.isEmpty()) {
                        throw new BeanCurrentlyInCreationException(beanName,
                                "Bean with name '" + beanName + "' has been injected into other beans [" +
                                StringUtils.collectionToCommaDelimitedString(actualDependentBeans) +
                                "] in its raw version as part of a circular reference, but has eventually been " +
                                "wrapped. This means that said other beans do not use the final version of the " +
                                "bean. This is often the result of over-eager type matching - consider using " +
                                "'getBeanNamesOfType' with the 'allowEagerInit' flag turned off, for example.");
                    }
                }
            }
        }

        try {
            //将bean添加到disposableBeans(singletons)的Map中,用于容器销毁时回调用 
            registerDisposableBeanIfNecessary(beanName, bean, mbd);
        }
        catch (BeanDefinitionValidationException ex) {
            throw new BeanCreationException(mbd.getResourceDescription(), beanName, "Invalid destruction signature", ex);
        }

        return exposedObject;
    }

至此IOC的依赖注入除了上面遗留的createBeanInstance和populateBean方法外,已经全部解析完成。
1)createBeanInstance
这个方法我们上面的描述是创建实例对象,而这个包含了代理的对象和class对象,下面我们来看看他的具体实现:

    /**
     * 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 BeanWrapper for the new instance
     */
    protected BeanWrapper createBeanInstance(String beanName, RootBeanDefinition mbd, Object[] args) {
        //确保这个点bean class已经被解析
        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());
        }

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

        //通过自动装配方法进行实例化
        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);
            }
        }

        //通过BeanPostProcessor来获取Constructor的数组
        Constructor<?>[] ctors = determineConstructorsFromBeanPostProcessors(beanClass, beanName);
        if (ctors != null ||
                mbd.getResolvedAutowireMode() == RootBeanDefinition.AUTOWIRE_CONSTRUCTOR ||
                mbd.hasConstructorArgumentValues() || !ObjectUtils.isEmpty(args))  {
            //使用容器的自动装配实例化
            return autowireConstructor(beanName, mbd, ctors, args);
        }

        //使用无参的构造函数实例化
        return instantiateBean(beanName, mbd);
    }

我们来看一下常用最常见的实例化过程instantiateBean

    /**
     * Instantiate the given bean using its default constructor.
     * @param beanName the name of the bean
     * @param mbd the bean definition for the bean
     * @return BeanWrapper for the new instance
     */
    protected BeanWrapper instantiateBean(final String beanName, final RootBeanDefinition mbd) {
        try {
            Object beanInstance;
            final BeanFactory parent = this;
            //系统的安全管理接口
            if (System.getSecurityManager() != null) {
                beanInstance = AccessController.doPrivileged(new PrivilegedAction<Object>() {
                    @Override
                    public Object run() {
                        return getInstantiationStrategy().instantiate(mbd, beanName, parent);
                    }
                }, getAccessControlContext());
            }
            else {
                //我们debug发现这里直接返回了bean的代理,这个方法中最为核心的代码  
                //debug进去发现进入了SimpleInstantiationStrategy类的instantiate方法
                //其实这里默认的实例化策略是 使用CGLIB来进行实例化的
                beanInstance = getInstantiationStrategy().instantiate(mbd, beanName, parent);
            }
            BeanWrapper bw = new BeanWrapperImpl(beanInstance);
            initBeanWrapper(bw);
            return bw;
        }
        catch (Throwable ex) {
            throw new BeanCreationException(mbd.getResourceDescription(), beanName, "Instantiation of bean failed", ex);
        }
    }

SimpleInstantiationStrategy类的instantiate方法实现

    @Override
    public Object instantiate(RootBeanDefinition bd, String beanName, BeanFactory owner) {
        //Bean定义中没有方法覆盖
        if (bd.getMethodOverrides().isEmpty()) {
            Constructor<?> constructorToUse;
            synchronized (bd.constructorArgumentLock) {
                //获取指定的构造器或生成对象的工厂方法
                constructorToUse = (Constructor<?>) bd.resolvedConstructorOrFactoryMethod;
                if (constructorToUse == null) {
                    //获取class对象
                    final Class<?> clazz = bd.getBeanClass();
                    //判断是否是接口
                    if (clazz.isInterface()) {
                        throw new BeanInstantiationException(clazz, "Specified class is an interface");
                    }
                    try {
                        if (System.getSecurityManager() != null) {
                            constructorToUse = AccessController.doPrivileged(new PrivilegedExceptionAction<Constructor<?>>() {
                                @Override
                                public Constructor<?> run() throws Exception {
                                    return clazz.getDeclaredConstructor((Class[]) null);
                                }
                            });
                        }
                        else {
                            //获取构造函数
                            constructorToUse =  clazz.getDeclaredConstructor((Class[]) null);
                        }
                        bd.resolvedConstructorOrFactoryMethod = constructorToUse;
                    }
                    catch (Exception ex) {
                        throw new BeanInstantiationException(clazz, "No default constructor found", ex);
                    }
                }
            }
            //使用JDK动态代理来实例化对象 
            return BeanUtils.instantiateClass(constructorToUse);
        }
        else {
            //使用CGLIB来实例化对象  
            return instantiateWithMethodInjection(bd, beanName, owner);
        }
    }

可以从上述代码发现代理对象只有2种方式生成,一种是JDK动态代理,一种是CGLIB。之后我们要解析的AOP也是通过这2种方式实现的。
2)populateBean
这个方法是对Bean对象的属性的处理(依赖关系的处理),下面我们来看看他的具体实现,为了生动形象的解释这个方法,我们先将我们的beans.xml的部分文件贴出来:

 <bean id="person" class="com.test.spring.PersonImpl" init-method="init" destroy-method="destroy">
     <property name="name" value="helloworld"></property>      
 </bean>
    /**
     * 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 BeanWrapper with bean instance
     */
    protected void populateBean(String beanName, RootBeanDefinition mbd, BeanWrapper bw) {
        //获取BeanDefinition中设置的Property值
        //debug的结果PropertyValues: length=1; bean property 'name'
        PropertyValues pvs = mbd.getPropertyValues();

        if (bw == null) {
            if (!pvs.isEmpty()) {
                throw new BeanCreationException(
                        mbd.getResourceDescription(), beanName, "Cannot apply property values to null instance");
            }
            else {
                // Skip property population phase for null instance.
                return;
            }
        }

        //通过调用Bean的PostProcessor后置处理器在设置属性之前先干一些事情
        //比如对bean的实例(这里一般是有createBeanInstance生成的代理)做一些修改
        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;
                    }
                }
            }
        }

        if (!continueWithPropertyPopulation) {
            return;
        }
       
        //依赖注入开始,首先处理autowire自动装配的注入
        //我们的beans.xml中的配置不走这段逻辑
        if (mbd.getResolvedAutowireMode() == RootBeanDefinition.AUTOWIRE_BY_NAME ||
                mbd.getResolvedAutowireMode() == RootBeanDefinition.AUTOWIRE_BY_TYPE) {
            MutablePropertyValues newPvs = new MutablePropertyValues(pvs);

            //根据Bean类型自动装配注入
            if (mbd.getResolvedAutowireMode() == RootBeanDefinition.AUTOWIRE_BY_NAME) {
                autowireByName(beanName, mbd, bw, newPvs);
            }

            //根据Bean类型自动装配注入 
            if (mbd.getResolvedAutowireMode() == RootBeanDefinition.AUTOWIRE_BY_TYPE) {
                autowireByType(beanName, mbd, bw, newPvs);
            }

            pvs = newPvs;
        }
        //检查容器是否有符合条件的后置处理器
        boolean hasInstAwareBpps = hasInstantiationAwareBeanPostProcessors();
        //检测Bean实例对象有没有依赖
        boolean needsDepCheck = (mbd.getDependencyCheck() != RootBeanDefinition.DEPENDENCY_CHECK_NONE);

        if (hasInstAwareBpps || needsDepCheck) {
            PropertyDescriptor[] filteredPds = filterPropertyDescriptorsForDependencyCheck(bw, mbd.allowCaching);
            if (hasInstAwareBpps) {
                for (BeanPostProcessor bp : getBeanPostProcessors()) {
                    if (bp instanceof InstantiationAwareBeanPostProcessor) {
                        InstantiationAwareBeanPostProcessor ibp = (InstantiationAwareBeanPostProcessor) bp;
                        //使用BeanPostProcessor处理器处理属性值  
                        pvs = ibp.postProcessPropertyValues(pvs, filteredPds, bw.getWrappedInstance(), beanName);
                        if (pvs == null) {
                            return;
                        }
                    }
                }
            }
            if (needsDepCheck) {
                //进行依赖检查  
                checkDependencies(beanName, mbd, filteredPds, pvs);
            }
        }
        //对属性进行注入
        applyPropertyValues(beanName, mbd, bw, pvs);
    }

    //对属性进行解析和注入,为了方便理解,我们把这几个参数的值先贴出来
    //beanName:person
    //mbd:Root bean: class [com.test.spring.PersonImpl]; scope=singleton; abstract=false; lazyInit=false; autowireMode=0; dependencyCheck=0; autowireCandidate=true; primary=false; factoryBeanName=null; factoryMethodName=null; initMethodName=init; destroyMethodName=destroy; defined in class path resource [beans.xml]
    //bw:org.springframework.beans.BeanWrapperImpl: wrapping object [com.test.spring.PersonImpl@7f552bd3]
    //pvs:PropertyValues: length=1; bean property 'name'
    protected void applyPropertyValues(String beanName, BeanDefinition mbd, BeanWrapper bw, PropertyValues pvs) {
        if (pvs == null || pvs.isEmpty()) {
            return;
        }
        //用来封装属性值 (pvs)
        MutablePropertyValues mpvs = null;
        List<PropertyValue> original;
        //安全机制
        if (System.getSecurityManager() != null) {
            if (bw instanceof BeanWrapperImpl) {
                ((BeanWrapperImpl) bw).setSecurityContext(getAccessControlContext());
            }
        }

        if (pvs instanceof MutablePropertyValues) {
            mpvs = (MutablePropertyValues) pvs;
            //判断属性值是否转换,这里第一次为false
            if (mpvs.isConverted()) {
                //为实例化对象设置属性值
                try {
                    bw.setPropertyValues(mpvs);
                    return;
                }
                catch (BeansException ex) {
                    throw new BeanCreationException(
                            mbd.getResourceDescription(), beanName, "Error setting property values", ex);
                }
            }
            //获取属性值对象的原始类型值 :[bean property 'name']
            original = mpvs.getPropertyValueList();
        }
        else {
            original = Arrays.asList(pvs.getPropertyValues());
        }
        //获取用户自定义的类型转换
        TypeConverter converter = getCustomTypeConverter();
        if (converter == null) {
            converter = bw;
        }
        //封装一个BeanDefinitionValueResolver,将Bean定义中的属性值解析为Bean实例对象的实际值
        BeanDefinitionValueResolver valueResolver = new BeanDefinitionValueResolver(this, beanName, mbd, converter);

        //这里为解析值创建一个副本,副本的数据将会被注入到bean中
        List<PropertyValue> deepCopy = new ArrayList<PropertyValue>(original.size());
        boolean resolveNecessary = false;
        //循环名为original的List
        for (PropertyValue pv : original) {
            //属性值不需要转换 
            if (pv.isConverted()) {
                deepCopy.add(pv);
            }
            //属性值需要转换 
            else {
                //property的名称
                String propertyName = pv.getName();
                //原始的属性值,即转换之前的属性值,debug的值为
                //TypedStringValue: value [helloworld], target type [null]
                Object originalValue = pv.getValue();
                //转换属性值,debug的值为helloworld
                Object resolvedValue = valueResolver.resolveValueIfNecessary(pv, originalValue);
                //转换之后的属性值 
                Object convertedValue = resolvedValue;
                //属性值是否可以转换
                boolean convertible = bw.isWritableProperty(propertyName) &&
                        !PropertyAccessorUtils.isNestedOrIndexedProperty(propertyName);
                if (convertible) {
                    //将给定的value值转换成指定要求的value
                    convertedValue = convertForProperty(resolvedValue, propertyName, bw, converter);
                }
                //存储转换后的属性值,避免每次属性注入时的转换工作  
                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();
        }

        //进行属性依赖注入  
        try {
            bw.setPropertyValues(new MutablePropertyValues(deepCopy));
        }
        catch (BeansException ex) {
            throw new BeanCreationException(
                    mbd.getResourceDescription(), beanName, "Error setting property values", ex);
        }
    }
至此,IOC的依赖注入中的getBean的方式我们已经分析完毕。这也就意味着IOC我们全部分析完了。里面或多或少的有些源码没分析到,如果大家想了解的话可以去参考《Spring技术内幕》这本书,然后结合debug的方式查看源码。
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 206,214评论 6 481
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 88,307评论 2 382
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 152,543评论 0 341
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 55,221评论 1 279
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 64,224评论 5 371
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 49,007评论 1 284
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 38,313评论 3 399
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 36,956评论 0 259
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 43,441评论 1 300
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 35,925评论 2 323
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 38,018评论 1 333
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 33,685评论 4 322
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 39,234评论 3 307
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 30,240评论 0 19
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 31,464评论 1 261
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 45,467评论 2 352
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 42,762评论 2 345

推荐阅读更多精彩内容