BeanDefinition到实例Bean的源码分析

#概述

spring ioc容器的核心类是AbstractApplicationContext,入口方法是refresh。这个方法是个模板方法,定义了加载到容器的全部过程。即spring将xml配置文件加载到内存的一个过程。(著名的dubbo分布式框架也利用了spring加载xml的机制,定制自己的xml解析器将对象接入到ioc容器中。)大致过程为:创建beanFactory用于存放转换后的信息->读取文件到输入流中->读取输入流里的数据,用NamespaceHandler里注册的解析器处理返回BeanDefinition->将BeanDefinition保存到DefaultListableBeanFactory的beanDefinitionMap中。

最终xml在spring中会放到一个以名称为key,beanDefinition为value的ConcurrentHashMap中。

当 BeanDefinition 注册完毕以后, Spring Bean 工厂就可以随时根据需要进行实例化了。

①:单例Bean:IOC启动时则实例化 ②:原型Bean:IOC启动时不实例化,真正使用时才实例化。

懒加载:只针对单例Bean,意思是IOC容器启动时单例Bean可以不实例化,真正调用的时候才实例化(类似原型Bean的初始化顺序)。 主要经过方法链:reflesh() 、 finishBeanFactoryInitialization (factory) 、 DefaultListableBeanFactory.preInstantiateSingletons (), 在这里会根据注册的 BeanDefinition 信息依此调用 getBean(beanName) 。而真正实例化的逻辑和 BeanFactory 是“殊途同归”的,所有有关 Bean 实例化都可以从 getBean(beanName) 入手。

#源码分析

##入口方法

public void refresh() throws BeansException, IllegalStateException {

    Object var1 = this.startupShutdownMonitor;
    synchronized(this.startupShutdownMonitor) {
        //准备刷新context
        this.prepareRefresh();
        //刷新子类beanFactory,注册beanDefinition
        ConfigurableListableBeanFactory beanFactory = this.obtainFreshBeanFactory();
        //准备beanfactory
        this.prepareBeanFactory(beanFactory);

        try {
            this.postProcessBeanFactory(beanFactory);
            this.invokeBeanFactoryPostProcessors(beanFactory);
            this.registerBeanPostProcessors(beanFactory);
            this.initMessageSource();
            this.initApplicationEventMulticaster();
            this.onRefresh();
            this.registerListeners();
            //初始化非懒加载的bean实例
            this.finishBeanFactoryInitialization(beanFactory);
            this.finishRefresh();
        } catch (BeansException var9) {
            if (this.logger.isWarnEnabled()) {
                this.logger.warn("Exception encountered during context initialization - cancelling refresh attempt: " + var9);
            }

            this.destroyBeans();
            this.cancelRefresh(var9);
            throw var9;
        } finally {
            this.resetCommonCaches();
        }

    }
}


protected void finishBeanFactoryInitialization(ConfigurableListableBeanFactory beanFactory) {
    
    if (beanFactory.containsBean("conversionService") && beanFactory.isTypeMatch("conversionService", ConversionService.class)) {
        beanFactory.setConversionService((ConversionService)beanFactory.getBean("conversionService", ConversionService.class));
    }

    if (!beanFactory.hasEmbeddedValueResolver()) {
        beanFactory.addEmbeddedValueResolver(new StringValueResolver() {
            public String resolveStringValue(String strVal) {
                return AbstractApplicationContext.this.getEnvironment().resolvePlaceholders(strVal);
            }
        });
    }

    String[] weaverAwareNames = beanFactory.getBeanNamesForType(LoadTimeWeaverAware.class, false, false);
    String[] var3 = weaverAwareNames;
    int var4 = weaverAwareNames.length;

    for(int var5 = 0; var5 < var4; ++var5) {
        String weaverAwareName = var3[var5];
        this.getBean(weaverAwareName);
    }

    beanFactory.setTempClassLoader((ClassLoader)null);
    beanFactory.freezeConfiguration();
    //初始化非懒加载的bean实例
    beanFactory.preInstantiateSingletons();
}

##初始化非懒加载的bean实例

public void preInstantiateSingletons() throws BeansException {
    if (this.logger.isDebugEnabled()) {
        this.logger.debug("Pre-instantiating singletons in " + this);
    }

    List<String> beanNames = new ArrayList(this.beanDefinitionNames);
    Iterator var2 = beanNames.iterator();

    while(true) {
        while(true) {
            String beanName;
            RootBeanDefinition bd;
            do {
                do {
                    do {
                        if (!var2.hasNext()) {
                            var2 = beanNames.iterator();

                            while(var2.hasNext()) {
                                beanName = (String)var2.next();
                                Object singletonInstance = this.getSingleton(beanName);
                                if (singletonInstance instanceof SmartInitializingSingleton) {
                                    final SmartInitializingSingleton smartSingleton = (SmartInitializingSingleton)singletonInstance;
                                    if (System.getSecurityManager() != null) {
                                        AccessController.doPrivileged(new PrivilegedAction<Object>() {
                                            public Object run() {
                                                smartSingleton.afterSingletonsInstantiated();
                                                return null;
                                            }
                                        }, this.getAccessControlContext());
                                    } else {
                                        smartSingleton.afterSingletonsInstantiated();
                                    }
                                }
                            }

                            return;
                        }

                        beanName = (String)var2.next();
                        bd = this.getMergedLocalBeanDefinition(beanName);
                    } while(bd.isAbstract());
                } while(!bd.isSingleton());
            } while(bd.isLazyInit());

            if (this.isFactoryBean(beanName)) {
                final FactoryBean<?> factory = (FactoryBean)this.getBean("&" + beanName);
                boolean isEagerInit;
                if (System.getSecurityManager() != null && factory instanceof SmartFactoryBean) {
                    isEagerInit = ((Boolean)AccessController.doPrivileged(new PrivilegedAction<Boolean>() {
                        public Boolean run() {
                            return ((SmartFactoryBean)factory).isEagerInit();
                        }
                    }, this.getAccessControlContext())).booleanValue();
                } else {
                    isEagerInit = factory instanceof SmartFactoryBean && ((SmartFactoryBean)factory).isEagerInit();
                }

                if (isEagerInit) {
                    this.getBean(beanName);
                }
            } else {
                this.getBean(beanName);
            }
        }
    }
}
复制代码

AbstractBeanFactory 有四个 getBean 的重载方法,不管调用哪个方法最终都是会调用另一个 doGetBean 方法:

public Object getBean(String name) throws BeansException {  
        return getBean(name, null, null);  
    }  
          
    public Object getBean(String name, Class requiredType) throws BeansException {  
        return getBean(name, requiredType, null);  
    }  
  
    public Object getBean(String name, Object[] args) throws BeansException {  
        return getBean(name, null, args);  
    }  
  
    /** 
     * Return an instance, which may be shared or independent, of the specified bean. 
     * @param name the name of the bean to retrieve 
     * @param requiredType the required type of the bean to retrieve 
     * @param args arguments to use if creating a prototype using explicit arguments to a 
     * static factory method. It is invalid to use a non-null args value in any other case. 
     * @return an instance of the bean 
     * @throws BeansException if the bean could not be created 
     */  
    public Object getBean(String name, Class requiredType, Object[] args) throws BeansException {  
        return doGetBean(name, requiredType, args, false);  
    }  


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

//bean name处理,去除FactoryBean前缀等  
     final String beanName = transformedBeanName(name);  
     Object bean = null;  
  
//先从singleton缓存中查看是否已经实例化过该Bean,根据是否有缓存分为两个分支分别处理  
    Object sharedInstance = getSingleton(beanName);  
    if (sharedInstance != null && args == null) {  
// 分支一,若缓存中获取到了并且该BeanDefinition信息表明该bean是singleton的,直接将获取到的缓存Bean  
//(有可能是半成品)交给getObjectForBeanInstance处理  
 /*.........省略logger部分代码............*/  
//调用getObjectForBeanInstance处理  
     bean = getObjectForBeanInstance(sharedInstance, name, beanName, null);  
    }else {  
// 分之二:没有缓存,则需要从头实例化该bean  
            // We're assumably within a circular reference.  
      if (isPrototypeCurrentlyInCreation(beanName)) {   
           throw new BeanCurrentlyInCreationException(beanName);
      }  
  
// 检查BeanDefinition是否在当前工厂或父工厂  
    BeanFactory parentBeanFactory = getParentBeanFactory();  
    if (parentBeanFactory != null && !containsBeanDefinition(beanName)) {  
        // Not found -> check parent.  
        String nameToLookup = originalBeanName(name);  
        if (args != null) {  
        // 父工厂getBean  
            return parentBeanFactory.getBean(nameToLookup, args);  
        }  
        else {  
            // No args -> delegate to standard getBean method.  
            return parentBeanFactory.getBean(nameToLookup, requiredType);  
        }  
    }  
//将bean加入“正在创建”的集合,完成后会remove,对应afterSingletonCreation/afterPrototypeCreation方法  
            if (!typeCheckOnly) {  
                markBeanAsCreated(beanName);  
            }  
  
            final RootBeanDefinition mbd = getMergedLocalBeanDefinition(beanName);  
            checkMergedBeanDefinition(mbd, beanName, args);  
  
// 解决依赖关系,将依赖的bean提前实例化  
    String[] dependsOn = mbd.getDependsOn();  
    if (dependsOn != null) {  
        for (int i = 0; i < dependsOn.length; i++) {  
            String dependsOnBean = dependsOn[i];  
            getBean(dependsOnBean);  
            registerDependentBean(dependsOnBean, beanName);  
        }  
    }  
  
// 这里又需要根据bean的类型分为三种情况:singleton、prototype、request/session  
    if (mbd.isSingleton()) {  
                   //通过自定义ObjectFactory实例化Bean,此结果可能是半成品(是FactoryBean等)  
        sharedInstance = getSingleton(beanName, new ObjectFactory() {  
            public Object getObject() throws BeansException {  
                try {  
                  //真正实例化装配的逻辑在createBean方法中  
                    return createBean(beanName, mbd, args);  
                }  
                catch (BeansException ex) {  
            // Explicitly remove instance from singleton cache: It might have been put there  
            // eagerly by the creation process, to allow for circular reference resolution.  
            // Also remove any beans that received a temporary reference to the bean.  
                            destroySingleton(beanName);  
                            throw ex;  
                        }  
                    }  
                });  
            //上一步半成品的Bean交给getObjectForBeanInstance方法处理  
                bean = getObjectForBeanInstance(sharedInstance, name, beanName, mbd);  
            }  
  
            else if (mbd.isPrototype()) {  
                // It's a prototype -> create a new instance.  
                Object prototypeInstance = null;  
                try {  
                    beforePrototypeCreation(beanName);  
                     //真正实例化装配的逻辑在createBean方法中  
                    prototypeInstance = createBean(beanName, mbd, args);  
                }  
                finally {  
                    afterPrototypeCreation(beanName);  
                }  
                    //上一步半成品的Bean交给getObjectForBeanInstance方法处理  
               bean = getObjectForBeanInstance(prototypeInstance, name, beanName, mbd);  
            }  
  
            else {  
                            //request、session 的bean  
                String scopeName = mbd.getScope();  
                final Scope scope = (Scope) this.scopes.get(scopeName);  
                if (scope == null) {  
        throw new IllegalStateException("No Scope registered for scope '" + scopeName + "'");  
                }  
                try {  
                    Object scopedInstance = scope.get(beanName, new ObjectFactory() {  
                        public Object getObject() throws BeansException {  
                            beforePrototypeCreation(beanName);  
                            try {  
                         //真正实例化装配的逻辑在createBean方法中  
                                return createBean(beanName, mbd, args);  
                            }  
                            finally {  
                                afterPrototypeCreation(beanName);  
                            }  
                        }  
                    });  
                       //上一步半成品的Bean交给getObjectForBeanInstance方法处理  
                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);  
                }  
            }  
        }  
  
        // Check if required type matches the type of the actual bean instance.  
        if (requiredType != null && bean != null &&  
                              !requiredType.isAssignableFrom(bean.getClass())) {  
            throw new BeanNotOfRequiredTypeException(name, requiredType, bean.getClass());  
        }  
        return bean;  
    }  
复制代码

通过注释,可以整理出较清晰的逻辑: 检查Bean缓存,已经有缓存的Bean对象(有可能是半成品)则交给getObjectForBeanInstance方法处理;否则先根据Bean的生命周期类型分别实例化,每种情况大致都分两步,第一步都交给createBean方法生产一个半成品的bean对象,然后同样是将半成品的bean交给getObjectForBeanInstance方法处理。

##以单例为例,是怎样实例化的

protected Object createBean(String beanName, RootBeanDefinition mbd, Object[] args) throws BeanCreationException {

    if (this.logger.isDebugEnabled()) {
        this.logger.debug("Creating instance of bean '" + beanName + "'");
    }

    RootBeanDefinition mbdToUse = mbd;
    Class<?> resolvedClass = this.resolveBeanClass(mbd, beanName, new Class[0]);
    if (resolvedClass != null && !mbd.hasBeanClass() && mbd.getBeanClassName() != null) {
        mbdToUse = new RootBeanDefinition(mbd);
        mbdToUse.setBeanClass(resolvedClass);
    }

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

    Object beanInstance;
    try {
        beanInstance = this.resolveBeforeInstantiation(beanName, mbdToUse);
        if (beanInstance != null) {
            return beanInstance;
        }
    } catch (Throwable var8) {
        throw new BeanCreationException(mbdToUse.getResourceDescription(), beanName, "BeanPostProcessor before instantiation of bean failed", var8);
    }

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

    return beanInstance;
}

##真正去创建bean

protected Object doCreateBean(final String beanName, final RootBeanDefinition mbd, Object[] args) throws BeanCreationException {

    BeanWrapper instanceWrapper = null;
    if (mbd.isSingleton()) {
        instanceWrapper = (BeanWrapper)this.factoryBeanInstanceCache.remove(beanName);
    }

    if (instanceWrapper == null) {
        instanceWrapper = this.createBeanInstance(beanName, mbd, args);
    }

    final Object bean = instanceWrapper != null ? instanceWrapper.getWrappedInstance() : null;
    Class<?> beanType = instanceWrapper != null ? instanceWrapper.getWrappedClass() : null;
    mbd.resolvedTargetType = beanType;
    Object var7 = mbd.postProcessingLock;
    synchronized(mbd.postProcessingLock) {
        if (!mbd.postProcessed) {
            try {
                this.applyMergedBeanDefinitionPostProcessors(mbd, beanType, beanName);
            } catch (Throwable var17) {
                throw new BeanCreationException(mbd.getResourceDescription(), beanName, "Post-processing of merged bean definition failed", var17);
            }

            mbd.postProcessed = true;
        }
    }

    boolean earlySingletonExposure = mbd.isSingleton() && this.allowCircularReferences && this.isSingletonCurrentlyInCreation(beanName);
    if (earlySingletonExposure) {
        if (this.logger.isDebugEnabled()) {
            this.logger.debug("Eagerly caching bean '" + beanName + "' to allow for resolving potential circular references");
        }

        this.addSingletonFactory(beanName, new ObjectFactory<Object>() {
            public Object getObject() throws BeansException {
                return AbstractAutowireCapableBeanFactory.this.getEarlyBeanReference(beanName, mbd, bean);
            }
        });
    }

    Object exposedObject = bean;

    try {
        this.populateBean(beanName, mbd, instanceWrapper);
        if (exposedObject != null) {
            exposedObject = this.initializeBean(beanName, exposedObject, mbd);
        }
    } catch (Throwable var18) {
        if (var18 instanceof BeanCreationException && beanName.equals(((BeanCreationException)var18).getBeanName())) {
            throw (BeanCreationException)var18;
        }

        throw new BeanCreationException(mbd.getResourceDescription(), beanName, "Initialization of bean failed", var18);
    }

    if (earlySingletonExposure) {
        Object earlySingletonReference = this.getSingleton(beanName, false);
        if (earlySingletonReference != null) {
            if (exposedObject == bean) {
                exposedObject = earlySingletonReference;
            } else if (!this.allowRawInjectionDespiteWrapping && this.hasDependentBean(beanName)) {
                String[] dependentBeans = this.getDependentBeans(beanName);
                Set<String> actualDependentBeans = new LinkedHashSet(dependentBeans.length);
                String[] var12 = dependentBeans;
                int var13 = dependentBeans.length;

                for(int var14 = 0; var14 < var13; ++var14) {
                    String dependentBean = var12[var14];
                    if (!this.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 {
        this.registerDisposableBeanIfNecessary(beanName, bean, mbd);
        return exposedObject;
    } catch (BeanDefinitionValidationException var16) {
        throw new BeanCreationException(mbd.getResourceDescription(), beanName, "Invalid destruction signature", var16);
    }
}


protected BeanWrapper createBeanInstance(String beanName, RootBeanDefinition mbd, Object[] args) {

    Class<?> beanClass = this.resolveBeanClass(mbd, beanName, new Class[0]);
    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());
    } else if (mbd.getFactoryMethodName() != null) {
        return this.instantiateUsingFactoryMethod(beanName, mbd, args);
    } else {
    
        boolean resolved = false;
        boolean autowireNecessary = false;
        if (args == null) {
            Object var7 = mbd.constructorArgumentLock;
            synchronized(mbd.constructorArgumentLock) {
                if (mbd.resolvedConstructorOrFactoryMethod != null) {
                    resolved = true;
                    autowireNecessary = mbd.constructorArgumentsResolved;
                }
            }
        }

        if (resolved) {
            return autowireNecessary ? this.autowireConstructor(beanName, mbd, (Constructor[])null, (Object[])null) : this.instantiateBean(beanName, mbd);
        } else {
            Constructor<?>[] ctors = this.determineConstructorsFromBeanPostProcessors(beanClass, beanName);
            return ctors == null && mbd.getResolvedAutowireMode() != 3 && !mbd.hasConstructorArgumentValues() && ObjectUtils.isEmpty(args) ? this.instantiateBean(beanName, mbd) : this.autowireConstructor(beanName, mbd, ctors, args);
        }
    }
}


protected BeanWrapper instantiateBean(final String beanName, final RootBeanDefinition mbd) {

    try {
        Object beanInstance;
        if (System.getSecurityManager() != null) {
            beanInstance = AccessController.doPrivileged(new PrivilegedAction<Object>() {
                public Object run() {
                    return AbstractAutowireCapableBeanFactory.this.getInstantiationStrategy().instantiate(mbd, beanName, AbstractAutowireCapableBeanFactory.this);
                }
            }, this.getAccessControlContext());
        } else {
            beanInstance = this.getInstantiationStrategy().instantiate(mbd, beanName, this);
        }

        BeanWrapper bw = new BeanWrapperImpl(beanInstance);
        this.initBeanWrapper(bw);
        return bw;
    } catch (Throwable var6) {
        throw new BeanCreationException(mbd.getResourceDescription(), beanName, "Instantiation of bean failed", var6);
    }
}


public class SimpleInstantiationStrategy implements InstantiationStrategy {
private static final ThreadLocal<Method> currentlyInvokedFactoryMethod = new ThreadLocal();

public SimpleInstantiationStrategy() {
}

public static Method getCurrentlyInvokedFactoryMethod() {
    return (Method)currentlyInvokedFactoryMethod.get();
}

public Object instantiate(RootBeanDefinition bd, String beanName, BeanFactory owner) {
    if (bd.getMethodOverrides().isEmpty()) {
        Object var5 = bd.constructorArgumentLock;
        Constructor constructorToUse;
        synchronized(bd.constructorArgumentLock) {
            constructorToUse = (Constructor)bd.resolvedConstructorOrFactoryMethod;
            if (constructorToUse == null) {
                final Class<?> clazz = bd.getBeanClass();
                if (clazz.isInterface()) {
                    throw new BeanInstantiationException(clazz, "Specified class is an interface");
                }

                try {
                    if (System.getSecurityManager() != null) {
                        constructorToUse = (Constructor)AccessController.doPrivileged(new PrivilegedExceptionAction<Constructor<?>>() {
                            public Constructor<?> run() throws Exception {
                                return clazz.getDeclaredConstructor((Class[])null);
                            }
                        });
                    } else {
                        constructorToUse = clazz.getDeclaredConstructor((Class[])null);
                    }

                    bd.resolvedConstructorOrFactoryMethod = constructorToUse;
                } catch (Throwable var9) {
                    throw new BeanInstantiationException(clazz, "No default constructor found", var9);
                }
            }
        }

        return BeanUtils.instantiateClass(constructorToUse, new Object[0]);
    } else {
        return this.instantiateWithMethodInjection(bd, beanName, owner);
    }
}复制代码
  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值