spring積累:@Autowired源碼解析

前言

在java開發(fā)過程中,基本都會用到spring,說起spring就會講到bean的生命周期,這里通過@autowired從源碼角度來講解bean的生命周期。

@Autowired

@Target({ElementType.CONSTRUCTOR, ElementType.METHOD, ElementType.PARAMETER, ElementType.FIELD, ElementType.ANNOTATION_TYPE})
@Retention(RetentionPolicy.RUNTIME)
@Documented
public @interface Autowired {

    /**
     * Declares whether the annotated dependency is required.
     * <p>Defaults to {@code true}.
     */
    boolean required() default true;

}

加上以上注解的方法,會spring容器中注入bean,具體源碼如下(忽略關聯(lián)性較弱代碼):

public class SpringBeanAutowiringInterceptor {
    /**
     * Autowire the target bean after construction as well as after passivation.
     * @param invocationContext the EJB3 invocation context
     */
    @PostConstruct
    @PostActivate
    public void autowireBean(InvocationContext invocationContext) {
        doAutowireBean(invocationContext.getTarget());
        try {
            invocationContext.proceed();
        }
        catch (RuntimeException ex) {
            doReleaseBean(invocationContext.getTarget());
            throw ex;
        }
        catch (Error err) {
            doReleaseBean(invocationContext.getTarget());
            throw err;
        }
        catch (Exception ex) {
            doReleaseBean(invocationContext.getTarget());
            // Cannot declare a checked exception on WebSphere here - so we need to wrap.
            throw new EJBException(ex);
        }
    }

    /**
     * Actually autowire the target bean after construction/passivation.
     * @param target the target bean to autowire
     */
    protected void doAutowireBean(Object target) {
        AutowiredAnnotationBeanPostProcessor bpp = new AutowiredAnnotationBeanPostProcessor();
        configureBeanPostProcessor(bpp, target);
        bpp.setBeanFactory(getBeanFactory(target));
        bpp.processInjection(target);
    }

    /**
     * Determine the BeanFactory for autowiring the given target bean.
     * @param target the target bean to autowire
     * @return the BeanFactory to use (never {@code null})
     * @see #getBeanFactoryReference
     */
    protected BeanFactory getBeanFactory(Object target) {
        BeanFactory factory = getBeanFactoryReference(target).getFactory();
        if (factory instanceof ApplicationContext) {
            factory = ((ApplicationContext) factory).getAutowireCapableBeanFactory();
        }
        return factory;
    }

    /**
     * Determine the BeanFactoryReference for the given target bean.
     * <p>The default implementation delegates to {@link #getBeanFactoryLocator}
     * and {@link #getBeanFactoryLocatorKey}.
     * @param target the target bean to autowire
     * @return the BeanFactoryReference to use (never {@code null})
     * @see #getBeanFactoryLocator
     * @see #getBeanFactoryLocatorKey
     * @see org.springframework.beans.factory.access.BeanFactoryLocator#useBeanFactory(String)
     */
    protected BeanFactoryReference getBeanFactoryReference(Object target) {
        String key = getBeanFactoryLocatorKey(target);
        BeanFactoryReference ref = getBeanFactoryLocator(target).useBeanFactory(key);
        this.beanFactoryReferences.put(target, ref);
        return ref;
    }
}
public class SingletonBeanFactoryLocator implements BeanFactoryLocator {
    @Override
    public BeanFactoryReference useBeanFactory(String factoryKey) throws BeansException {
        synchronized (this.bfgInstancesByKey) {
            ......
            try {
                BeanFactory beanFactory;
                if (factoryKey != null) {
                    beanFactory = bfg.definition.getBean(factoryKey, BeanFactory.class);
                }
                else {
                    beanFactory = bfg.definition.getBean(BeanFactory.class);
                }
                return new CountingBeanFactoryReference(beanFactory, bfg.definition);
            }
            catch (BeansException ex) {
                throw new BootstrapException("Unable to return specified BeanFactory instance: factory key [" +
                        factoryKey + "], from group with resource name [" + this.resourceLocation + "]", ex);
            }

        }
    }
}
public class DefaultListableBeanFactory extends AbstractAutowireCapableBeanFactory
        implements ConfigurableListableBeanFactory, BeanDefinitionRegistry, Serializable {
    @Override
    public <T> T getBean(Class<T> requiredType, Object... args) throws BeansException {
        NamedBeanHolder<T> namedBean = resolveNamedBean(requiredType, args);
        if (namedBean != null) {
            return namedBean.getBeanInstance();
        }
        BeanFactory parent = getParentBeanFactory();
        if (parent != null) {
            return parent.getBean(requiredType, args);
        }
        throw new NoSuchBeanDefinitionException(requiredType);
    }
}
public abstract class AbstractBeanFactory extends FactoryBeanRegistrySupport implements ConfigurableBeanFactory {
    public <T> T getBean(String name, Class<T> requiredType, Object... args) throws BeansException {
        return doGetBean(name, requiredType, args, false);
    }

    protected <T> T doGetBean(
            final String name, final Class<T> requiredType, final Object[] args, boolean typeCheckOnly)
            throws BeansException {

    ......
                                    return createBean(beanName, mbd, args);

    ......
    }
public abstract class AbstractAutowireCapableBeanFactory extends AbstractBeanFactory
        implements AutowireCapableBeanFactory {
    /**
     * Central method of this class: creates a bean instance,
     * populates the bean instance, applies post-processors, etc.
     * @see #doCreateBean
         * 1.根據設置的class屬性或者className來解析、加載class
         * 2.對override屬性進行標記和驗證(bean XML配置中的lookup-method和replace-method屬性)
        * 3.應用初始化前的后處理器,如果處理器中返回了AOP的代理對象,則直接返回該單例對象,不需要繼續(xù)創(chuàng)建
        * 4.創(chuàng)建bean
     */
    @Override
    protected Object createBean(String beanName, RootBeanDefinition mbd, Object[] args) throws BeanCreationException {
        if (logger.isDebugEnabled()) {
            logger.debug("Creating instance of bean '" + beanName + "'");
        }
        RootBeanDefinition mbdToUse = mbd;

        // Make sure bean class is actually resolved at this point, and
        // clone the bean definition in case of a dynamically resolved Class
        // which cannot be stored in the shared merged bean definition.
        Class<?> resolvedClass = resolveBeanClass(mbd, beanName);
        if (resolvedClass != null && !mbd.hasBeanClass() && mbd.getBeanClassName() != null) {
            mbdToUse = new RootBeanDefinition(mbd);
            mbdToUse.setBeanClass(resolvedClass);
        }

        // Prepare method overrides.
        try {
            mbdToUse.prepareMethodOverrides();
        }
        catch (BeanDefinitionValidationException ex) {
            throw new BeanDefinitionStoreException(mbdToUse.getResourceDescription(),
                    beanName, "Validation of method overrides failed", ex);
        }

        try {
            // Give BeanPostProcessors a chance to return a proxy instead of the target bean instance.
            Object bean = resolveBeforeInstantiation(beanName, mbdToUse);
            if (bean != null) {
                return bean;
            }
        }
        catch (Throwable ex) {
            throw new BeanCreationException(mbdToUse.getResourceDescription(), beanName,
                    "BeanPostProcessor before instantiation of bean failed", ex);
        }

        Object beanInstance = doCreateBean(beanName, mbdToUse, args);
        if (logger.isDebugEnabled()) {
            logger.debug("Finished creating instance of bean '" + beanName + "'");
        }
        return beanInstance;
    }

    // 1.如果是單例則首先清除緩存
    // 2.實例化bean,并使用BeanWarpper包裝
    // 3.如果存在工廠方法,則使用工廠方法實例化
    // 4.如果有多個構造函數(shù),則根據傳入的參數(shù)確定構造函數(shù)進行初始化使用默認的構造函數(shù)初始化
    // 5.調用MergedBeanDefinitionPostProcessor,Autowired注解就是在這樣完成的預解析工作
    // 6.依賴處理。如果A和B存在循環(huán)依賴,那么Spring在創(chuàng)建B的時候,需要自動注入A時,并不會直接創(chuàng)建再次創(chuàng)建A,而是通過放入緩存中A的ObjectFactory來創(chuàng)建實例,這樣就解決了循環(huán)依賴的問題
    // 7.屬性填充。所有需要的屬性都在這一步注入到bean
    // 8.循環(huán)依賴檢查
    // 9.注冊DisposableBean。如果配置了destroy-method,這里需要注冊,以便在銷毀時調用
    // 10.完成創(chuàng)建并返回
    protected Object doCreateBean(final String beanName, final RootBeanDefinition mbd, final Object[] args)
            throws BeanCreationException {
        // Instantiate the bean.
        BeanWrapper instanceWrapper = null;
        if (mbd.isSingleton()) {
            //先嘗試從緩存中取出
            instanceWrapper = this.factoryBeanInstanceCache.remove(beanName);
        }

        //如果緩存沒有命中則根據對應的策略創(chuàng)建實例
        if (instanceWrapper == null) {
            instanceWrapper = createBeanInstance(beanName, mbd, args);
        }

        // Allow post-processors to modify the merged bean definition.
        synchronized (mbd.postProcessingLock) {
            //調用MergedBeanDefinitionPostProcessor 后處理器,合并bean的定義信息
            //Autowire等注解信息就是在這一步完成預解析,并且將注解需要的信息放入緩存
            if (!mbd.postProcessed) {
                try {
                    applyMergedBeanDefinitionPostProcessors(mbd, beanType, beanName);
                }
                catch (Throwable ex) {
                    throw new BeanCreationException(mbd.getResourceDescription(), beanName,
                            "Post-processing of merged bean definition failed", ex);
                }
                mbd.postProcessed = true;
            }
        }

        // Initialize the bean instance.
        Object exposedObject = bean;
        try {
            populateBean(beanName, mbd, instanceWrapper);
            if (exposedObject != null) {
                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);
            }
        }
    }

    protected BeanWrapper createBeanInstance(String beanName, RootBeanDefinition mbd, Object[] args) {
    // Make sure bean class is actually resolved at this point.
        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);
        }

        // 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);
            }
        }

        // Need to determine the 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);
        }

        // No special handling: simply use no-arg constructor.
        return instantiateBean(beanName, mbd);
    }

    /**
     * Apply MergedBeanDefinitionPostProcessors to the specified bean definition,
     * invoking their {@code postProcessMergedBeanDefinition} methods.
     * @param mbd the merged bean definition for the bean
     * @param beanType the actual type of the managed bean instance
     * @param beanName the name of the bean
     * @see MergedBeanDefinitionPostProcessor#postProcessMergedBeanDefinition
     */
    protected void applyMergedBeanDefinitionPostProcessors(RootBeanDefinition mbd, Class<?> beanType, String beanName) {
        for (BeanPostProcessor bp : getBeanPostProcessors()) {
            if (bp instanceof MergedBeanDefinitionPostProcessor) {
                MergedBeanDefinitionPostProcessor bdp = (MergedBeanDefinitionPostProcessor) bp;
                bdp.postProcessMergedBeanDefinition(mbd, beanType, beanName);
            }
        }
    }

    /**
     * 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) {
        if (mbd.getResolvedAutowireMode() == RootBeanDefinition.AUTOWIRE_BY_NAME ||
                mbd.getResolvedAutowireMode() == RootBeanDefinition.AUTOWIRE_BY_TYPE) {
            MutablePropertyValues newPvs = new MutablePropertyValues(pvs);

            // Add property values based on autowire by name if applicable.
            if (mbd.getResolvedAutowireMode() == RootBeanDefinition.AUTOWIRE_BY_NAME) {
                autowireByName(beanName, mbd, bw, newPvs);
            }

            // Add property values based on autowire by type if applicable.
            if (mbd.getResolvedAutowireMode() == RootBeanDefinition.AUTOWIRE_BY_TYPE) {
                autowireByType(beanName, mbd, bw, newPvs);
            }

            pvs = newPvs;
        }

        boolean hasInstAwareBpps = hasInstantiationAwareBeanPostProcessors();
        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;
                        pvs = ibp.postProcessPropertyValues(pvs, filteredPds, bw.getWrappedInstance(), beanName);
                        if (pvs == null) {
                            return;
                        }
                    }
                }
            }
            if (needsDepCheck) {
                checkDependencies(beanName, mbd, filteredPds, pvs);
            }
        }
    }

    /**
     * Fill in any missing property values with references to
     * other beans in this factory if autowire is set to "byName".
     * @param beanName the name of the bean we're wiring up.
     * Useful for debugging messages; not used functionally.
     * @param mbd bean definition to update through autowiring
     * @param bw BeanWrapper from which we can obtain information about the bean
     * @param pvs the PropertyValues to register wired objects with
     */
    protected void autowireByName(
            String beanName, AbstractBeanDefinition mbd, BeanWrapper bw, MutablePropertyValues pvs) {

        String[] propertyNames = unsatisfiedNonSimpleProperties(mbd, bw);
        for (String propertyName : propertyNames) {
            if (containsBean(propertyName)) {
                Object bean = getBean(propertyName);
                pvs.add(propertyName, bean);
                registerDependentBean(propertyName, beanName);
                if (logger.isDebugEnabled()) {
                    logger.debug("Added autowiring by name from bean name '" + beanName +
                            "' via property '" + propertyName + "' to bean named '" + propertyName + "'");
                }
            }
            else {
                if (logger.isTraceEnabled()) {
                    logger.trace("Not autowiring property '" + propertyName + "' of bean '" + beanName +
                            "' by name: no matching bean found");
                }
            }
        }
    }
}
public class AutowiredAnnotationBeanPostProcessor extends InstantiationAwareBeanPostProcessorAdapter
        implements MergedBeanDefinitionPostProcessor, PriorityOrdered, BeanFactoryAware {
    @Override
    public PropertyValues postProcessPropertyValues(
            PropertyValues pvs, PropertyDescriptor[] pds, Object bean, String beanName) throws BeanCreationException {

        InjectionMetadata metadata = findAutowiringMetadata(beanName, bean.getClass(), pvs);
        try {
            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;
    }
}
?著作權歸作者所有,轉載或內容合作請聯(lián)系作者
【社區(qū)內容提示】社區(qū)部分內容疑似由AI輔助生成,瀏覽時請結合常識與多方信息審慎甄別。
平臺聲明:文章內容(如有圖片或視頻亦包括在內)由作者上傳并發(fā)布,文章內容僅代表作者本人觀點,簡書系信息發(fā)布平臺,僅提供信息存儲服務。

相關閱讀更多精彩內容

友情鏈接更多精彩內容