Spring源码阅读3-bean获取-上
2015-12-05 16:56
489 查看
继续前面的话题,当我们已经将bean的定义从xml文件获取到容器后(包括使用注解的自动扫描),下面要进行的就是bean的获取了。现在我们的容器拥有了bean的所有信息,包括类型,class对象,属性参数,单例or原型,初始化参数,注入参数注入类型等等,那么我们是不是就可以获取这个bean的对象了?直接从源码开始:
看下DefaultListableBeanFactory的成员变量,可以看到前两篇文章谈到的bean加载,都已经加载并放在了相应变量容器中。
根据bean的name获取bean对象,调用DefaultListableBeanFactory的getBean方法,实际是调用父类AbstractBeanFactory的方法:
继续跟踪:
方法有些长,我们只关心重点,首先从单例缓存中查看目标对象,若存在则直接获取并返回,若未获取到,则查看线程本地对象:
这个对象存放了正在创建中,且未创建完成的对象(已完成的对象,是单例的会进入刚才的单例缓存),若线程本地中存在,则说明发生了同时创建的情况(有可能是循环依赖,对象创建的时候,查看是否有注入对象,并创建注入对象,而注入对象又存在了注入本对象的情况,此时会循环创建),抛出异常。
经过上述两次过程之后,未获取到对象,也为抛出异常,进行第三步:在父类工厂容器中查看是否有此对象,若存在并返回,若不存在,进行第四步,即创建新对象。
这里我们只关注新对象的创建过程,而新对象的创建,重点就在上述函数的这一段代码里,为了方便阅读,再次拷贝一下:
首先获取对象所依赖的类,若存在,则进行依赖注入的校验,验证目标对象的依赖类型是否也依赖了对象自身,若存在循环依赖情况则抛出异常,否则,将依赖对象放入dependentBeanMap(key:beanName-->value: Set of dependent bean name),然后进入依赖对象的创建过程(若此对象还未创建)。经过上述流程,我们开始真正去观察一个类从bean定义到实例化的过程。这里又分为原型和单例两种,我们看下单例对象的加载:
当对象尚未创建完且又重复创建的时候,会去earlySingletonObjects以及singletonsCurrentlyInCreation中进行获取验证。继续进行到代码:
这里调用了外层的回调函数,singletonFactory.getObject()方法中调用了createBean(beanName, mbd, args);跟踪到此方法,进入到AbstractAutowireCapableBeanFactory的createBean方法中:
对于resolveBeanClass方法,就不上源码了,主要是检查了class类型,然后获取ClassLoader并加载class,获得class对象并放入到BeanDefinition以便后面使用。
mbdToUse.prepareMethodOverrides();是对override的处理,这里是对Spring中lockup-method和replace-method的处理,这两个配置加载其实就是将配置同意放在BeanDefiition中的methodOverrides属性里,在这里通过代理实现重写。
给BeanPostProcessors一个返回代理对象的机会。
查看了类型后我们发现,InstantiationAwareBeanPostProcessor并没有实际实现类,唯一的子接口的实现类InstantiationAwareBeanPostProcessorAdapter是一个抽象类,
postProcessBeforeInstantiation和postProcessAfterInstantiation直接返回null;并没有做任何处理,其实这个是Spring留给用户的一个扩展,用户可以自己实现InstantiationAwareBeanPostProcessor以及处理方法,来获取用户想要的代理对象。而真正创建Bean的方法:
进一步跟踪createBeanInstance方法,
从这个方法的注释可以看出,createBeanInstance方法使用正确的方式如工厂方法,构造函数autowiring或简单实例化,为指定的bean创建实例对象,首先
如果BeanDefinition存在工厂方法名,则使用工厂方法创建对象,否则,进行下一步,若autowireNecessary条件成立,则使用构造方法注入,创建对象,进一步跟踪方法:
构造方法注入实例化对象,到这里就不再谈了,有兴趣可以自己看源码,内容比较复杂,这里进行了构造方法的排序,筛选,决策要使用构造方法等。我们常用的都是set方法注入,所以跳过这里,直接去看另一种情况。
直接实例化Bean:
看下DefaultListableBeanFactory的成员变量,可以看到前两篇文章谈到的bean加载,都已经加载并放在了相应变量容器中。
/** Map from serialized id to factory instance */ private static final Map<String, Reference<DefaultListableBeanFactory>> serializableFactories = new ConcurrentHashMap<String, Reference<DefaultListableBeanFactory>>(8); /** Optional id for this factory, for serialization purposes */ private String serializationId; /** Whether to allow re-registration of a different definition with the same name */ private boolean allowBeanDefinitionOverriding = true; /** Whether to allow eager class loading even for lazy-init beans */ private boolean allowEagerClassLoading = true; /** Optional OrderComparator for dependency Lists and arrays */ private Comparator<Object> dependencyComparator; /** Resolver to use for checking if a bean definition is an autowire candidate */ private AutowireCandidateResolver autowireCandidateResolver = new SimpleAutowireCandidateResolver(); /** Map from dependency type to corresponding autowired value */ private final Map<Class<?>, Object> resolvableDependencies = new ConcurrentHashMap<Class<?>, Object>(16); /** Map of bean definition objects, keyed by bean name */ private final Map<String, BeanDefinition> beanDefinitionMap = new ConcurrentHashMap<String, BeanDefinition>(64); /** Map of singleton and non-singleton bean names, keyed by dependency type */ private final Map<Class<?>, String[]> allBeanNamesByType = new ConcurrentHashMap<Class<?>, String[]>(64); /** Map of singleton-only bean names, keyed by dependency type */ private final Map<Class<?>, String[]> singletonBeanNamesByType = new ConcurrentHashMap<Class<?>, String[]>(64); /** List of bean definition names, in registration order */ private volatile List<String> beanDefinitionNames = new ArrayList<String>(64); /** List of names of manually registered singletons, in registration order */ private volatile Set<String> manualSingletonNames = new LinkedHashSet<String>(16); /** Cached array of bean definition names in case of frozen configuration */ private volatile String[] frozenBeanDefinitionNames; /** Whether bean definition metadata may be cached for all beans */ private volatile boolean configurationFrozen = false;
根据bean的name获取bean对象,调用DefaultListableBeanFactory的getBean方法,实际是调用父类AbstractBeanFactory的方法:
@Override public Object getBean(String name) throws BeansException { return doGetBean(name, null, null, false); }
继续跟踪:
@SuppressWarnings("unchecked") protected <T> T doGetBean(final String name, final Class<T> requiredType, final Object[] args, boolean typeCheckOnly) throws BeansException { final String beanName = transformedBeanName(name); Object bean; // Eagerly check singleton cache for manually registered singletons. 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 = getObjectForBeanInstance(sharedInstance, name, beanName, null); } else { // Fail if we're already creating this bean instance: // We're assumably within a circular reference. if (isPrototypeCurrentlyInCreation(beanName)) { throw new BeanCurrentlyInCreationException(beanName); } // Check if bean definition exists in this factory. BeanFactory parentBeanFactory = getParentBeanFactory(); if (parentBeanFactory != null && !containsBeanDefinition(beanName)) { // Not found -> check parent. 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); } } if (!typeCheckOnly) { markBeanAsCreated(beanName); } try { final RootBeanDefinition mbd = getMergedLocalBeanDefinition(beanName); checkMergedBeanDefinition(mbd, beanName, args); // Guarantee initialization of beans that the current bean depends on. String[] dependsOn = mbd.getDependsOn(); if (dependsOn != null) { for (String dependsOnBean : dependsOn) { if (isDependent(beanName, dependsOnBean)) { throw new BeanCreationException(mbd.getResourceDescription(), beanName, "Circular depends-on relationship between '" + beanName + "' and '" + dependsOnBean + "'"); } registerDependentBean(dependsOnBean, beanName); getBean(dependsOnBean); } } // Create bean instance. if (mbd.isSingleton()) { sharedInstance = getSingleton(beanName, new ObjectFactory<Object>() { @Override public Object getObject() throws BeansException { try { 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(sharedInstance, name, beanName, mbd); } else if (mbd.isPrototype()) { // It's a prototype -> create a new instance. Object prototypeInstance = null; try { beforePrototypeCreation(beanName); prototypeInstance = createBean(beanName, mbd, args); } finally { afterPrototypeCreation(beanName); } bean = getObjectForBeanInstance(prototypeInstance, name, beanName, mbd); } else { String scopeName = mbd.getScope(); final 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<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; } } // Check if required type matches the type of the actual bean instance. if (requiredType != null && bean != null && !requiredType.isAssignableFrom(bean.getClass())) { try { 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()); } } return (T) bean; }
方法有些长,我们只关心重点,首先从单例缓存中查看目标对象,若存在则直接获取并返回,若未获取到,则查看线程本地对象:
/** Names of beans that are currently in creation */ private final ThreadLocal<Object> prototypesCurrentlyInCreation = new NamedThreadLocal<Object>( "Prototype beans currently in creation");
这个对象存放了正在创建中,且未创建完成的对象(已完成的对象,是单例的会进入刚才的单例缓存),若线程本地中存在,则说明发生了同时创建的情况(有可能是循环依赖,对象创建的时候,查看是否有注入对象,并创建注入对象,而注入对象又存在了注入本对象的情况,此时会循环创建),抛出异常。
经过上述两次过程之后,未获取到对象,也为抛出异常,进行第三步:在父类工厂容器中查看是否有此对象,若存在并返回,若不存在,进行第四步,即创建新对象。
这里我们只关注新对象的创建过程,而新对象的创建,重点就在上述函数的这一段代码里,为了方便阅读,再次拷贝一下:
try { final RootBeanDefinition mbd = getMergedLocalBeanDefinition(beanName); checkMergedBeanDefinition(mbd, beanName, args); // Guarantee initialization of beans that the current bean depends on. String[] dependsOn = mbd.getDependsOn(); if (dependsOn != null) { for (String dependsOnBean : dependsOn) { if (isDependent(beanName, dependsOnBean)) { throw new BeanCreationException(mbd.getResourceDescription(), beanName, "Circular depends-on relationship between '" + beanName + "' and '" + dependsOnBean + "'"); } registerDependentBean(dependsOnBean, beanName); getBean(dependsOnBean); } } // Create bean instance. if (mbd.isSingleton()) { sharedInstance = getSingleton(beanName, new ObjectFactory<Object>() { @Override public Object getObject() throws BeansException { try { 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(sharedInstance, name, beanName, mbd); } else if (mbd.isPrototype()) { // It's a prototype -> create a new instance. Object prototypeInstance = null; try { beforePrototypeCreation(beanName); prototypeInstance = createBean(beanName, mbd, args); } finally { afterPrototypeCreation(beanName); } bean = getObjectForBeanInstance(prototypeInstance, name, beanName, mbd); } else { String scopeName = mbd.getScope(); final 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<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; } }
首先获取对象所依赖的类,若存在,则进行依赖注入的校验,验证目标对象的依赖类型是否也依赖了对象自身,若存在循环依赖情况则抛出异常,否则,将依赖对象放入dependentBeanMap(key:beanName-->value: Set of dependent bean name),然后进入依赖对象的创建过程(若此对象还未创建)。经过上述流程,我们开始真正去观察一个类从bean定义到实例化的过程。这里又分为原型和单例两种,我们看下单例对象的加载:
// Create bean instance. if (mbd.isSingleton()) { sharedInstance = getSingleton(beanName, new ObjectFactory<Object>() { @Override public Object getObject() throws BeansException { try { 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(sharedInstance, name, beanName, mbd); }
/** * Return the (raw) singleton object registered under the given name, * creating and registering a new one if none registered yet. * @param beanName the name of the bean * @param singletonFactory the ObjectFactory to lazily create the singleton * with, if necessary * @return the registered singleton object */ public Object getSingleton(String beanName, ObjectFactory<?> singletonFactory) { Assert.notNull(beanName, "'beanName' must not be null"); synchronized (this.singletonObjects) { Object singletonObject = this.singletonObjects.get(beanName); if (singletonObject == null) { if (this.singletonsCurrentlyInDestruction) { throw new BeanCreationNotAllowedException(beanName, "Singleton bean creation not allowed while the singletons of this factory are in destruction " + "(Do not request a bean from a BeanFactory in a destroy method implementation!)"); } if (logger.isDebugEnabled()) { logger.debug("Creating shared instance of singleton bean '" + beanName + "'"); } beforeSingletonCreation(beanName); boolean newSingleton = false; boolean recordSuppressedExceptions = (this.suppressedExceptions == null); if (recordSuppressedExceptions) { this.suppressedExceptions = new LinkedHashSet<Exception>(); } try { singletonObject = singletonFactory.getObject(); newSingleton = true; } catch (IllegalStateException ex) { // Has the singleton object implicitly appeared in the meantime -> // if yes, proceed with it since the exception indicates that state. singletonObject = this.singletonObjects.get(beanName); if (singletonObject == null) { throw ex; } } catch (BeanCreationException ex) { if (recordSuppressedExceptions) { for (Exception suppressedException : this.suppressedExceptions) { ex.addRelatedCause(suppressedException); } } throw ex; } finally { if (recordSuppressedExceptions) { this.suppressedExceptions = null; } afterSingletonCreation(beanName); } if (newSingleton) { addSingleton(beanName, singletonObject); } } return (singletonObject != NULL_OBJECT ? singletonObject : null); } }在beforeSingletonCreation方法中,进行了一些验证,以及将beanName放到singletonsCurrentlyInCreation对象中,这里就是我们说的,Spring解决循环依赖似是通过提前曝光到map中实现的:
protected void beforeSingletonCreation(String beanName) { if (!this.inCreationCheckExclusions.contains(beanName) && !this.singletonsCurrentlyInCreation.add(beanName)) { throw new BeanCurrentlyInCreationException(beanName); } }
当对象尚未创建完且又重复创建的时候,会去earlySingletonObjects以及singletonsCurrentlyInCreation中进行获取验证。继续进行到代码:
try { singletonObject = singletonFactory.getObject(); newSingleton = true; }
这里调用了外层的回调函数,singletonFactory.getObject()方法中调用了createBean(beanName, mbd, args);跟踪到此方法,进入到AbstractAutowireCapableBeanFactory的createBean方法中:
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; }
对于resolveBeanClass方法,就不上源码了,主要是检查了class类型,然后获取ClassLoader并加载class,获得class对象并放入到BeanDefinition以便后面使用。
mbdToUse.prepareMethodOverrides();是对override的处理,这里是对Spring中lockup-method和replace-method的处理,这两个配置加载其实就是将配置同意放在BeanDefiition中的methodOverrides属性里,在这里通过代理实现重写。
// Give BeanPostProcessors a chance to return a proxy instead of the target bean instance. Object bean = resolveBeforeInstantiation(beanName, mbdToUse);
给BeanPostProcessors一个返回代理对象的机会。
/** * Apply before-instantiation post-processors, resolving whether there is a * before-instantiation shortcut for the specified bean. * @param beanName the name of the bean * @param mbd the bean definition for the bean * @return the shortcut-determined bean instance, or {@code null} if none */ 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; }
/** * Apply InstantiationAwareBeanPostProcessors to the specified bean definition * (by class and name), invoking their {@code postProcessBeforeInstantiation} methods. * <p>Any returned object will be used as the bean instead of actually instantiating * the target bean. A {@code null} return value from the post-processor will * result in the target bean being instantiated. * @param beanClass the class of the bean to be instantiated * @param beanName the name of the bean * @return the bean object to use instead of a default instance of the target bean, or {@code null} * @throws BeansException if any post-processing failed * @see InstantiationAwareBeanPostProcessor#postProcessBeforeInstantiation */ protected Object applyBeanPostProcessorsBeforeInstantiation(Class<?> beanClass, String beanName) throws BeansException { for (BeanPostProcessor bp : getBeanPostProcessors()) { if (bp instanceof InstantiationAwareBeanPostProcessor) { InstantiationAwareBeanPostProcessor ibp = (InstantiationAwareBeanPostProcessor) bp; Object result = ibp.postProcessBeforeInstantiation(beanClass, beanName); if (result != null) { return result; } } } return null; }
@Override public Object applyBeanPostProcessorsAfterInitialization(Object existingBean, String beanName) throws BeansException { Object result = existingBean; for (BeanPostProcessor beanProcessor : getBeanPostProcessors()) { result = beanProcessor.postProcessAfterInitialization(result, beanName); if (result == null) { return result; } } return result; }
查看了类型后我们发现,InstantiationAwareBeanPostProcessor并没有实际实现类,唯一的子接口的实现类InstantiationAwareBeanPostProcessorAdapter是一个抽象类,
postProcessBeforeInstantiation和postProcessAfterInstantiation直接返回null;并没有做任何处理,其实这个是Spring留给用户的一个扩展,用户可以自己实现InstantiationAwareBeanPostProcessor以及处理方法,来获取用户想要的代理对象。而真正创建Bean的方法:
Object beanInstance = doCreateBean(beanName, mbdToUse, args);
protected Object doCreateBean(final String beanName, final RootBeanDefinition mbd, final Object[] args) { // Instantiate the bean. BeanWrapper instanceWrapper = null; if (mbd.isSingleton()) { instanceWrapper = this.factoryBeanInstanceCache.remove(beanName); } if (instanceWrapper == null) { instanceWrapper = createBeanInstance(beanName, mbd, args); } final Object bean = (instanceWrapper != null ? instanceWrapper.getWrappedInstance() : null); Class<?> beanType = (instanceWrapper != null ? instanceWrapper.getWrappedClass() : null); // Allow post-processors to modify the merged bean definition. synchronized (mbd.postProcessingLock) { if (!mbd.postProcessed) { applyMergedBeanDefinitionPostProcessors(mbd, beanType, beanName); mbd.postProcessed = true; } } // Eagerly cache singletons to be able to resolve circular references // even when triggered by lifecycle interfaces like BeanFactoryAware. 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"); } addSingletonFactory(beanName, new ObjectFactory<Object>() { @Override public Object getObject() throws BeansException { return getEarlyBeanReference(beanName, mbd, bean); } }); } // 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); } } if (earlySingletonExposure) { Object earlySingletonReference = getSingleton(beanName, false); if (earlySingletonReference != null) { if (exposedObject == bean) { exposedObject = earlySingletonReference; } else if (!this.allowRawInjectionDespiteWrapping && hasDependentBean(beanName)) { String[] dependentBeans = getDependentBeans(beanName); Set<String> actualDependentBeans = new LinkedHashSet<String>(dependentBeans.length); for (String dependentBean : dependentBeans) { 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."); } } } } // Register bean as disposable. try { registerDisposableBeanIfNecessary(beanName, bean, mbd); } catch (BeanDefinitionValidationException ex) { throw new BeanCreationException(mbd.getResourceDescription(), beanName, "Invalid destruction signature", ex); } return exposedObject; }
进一步跟踪createBeanInstance方法,
/** * 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 * @see #instantiateUsingFactoryMethod * @see #autowireConstructor * @see #instantiateBean */ 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); }
从这个方法的注释可以看出,createBeanInstance方法使用正确的方式如工厂方法,构造函数autowiring或简单实例化,为指定的bean创建实例对象,首先
if (mbd.getFactoryMethodName() != null) { return instantiateUsingFactoryMethod(beanName, mbd, args); }
如果BeanDefinition存在工厂方法名,则使用工厂方法创建对象,否则,进行下一步,若autowireNecessary条件成立,则使用构造方法注入,创建对象,进一步跟踪方法:
/** * "autowire constructor" (with constructor arguments by type) behavior. * Also applied if explicit constructor argument values are specified, * matching all remaining arguments with beans from the bean factory. * <p>This corresponds to constructor injection: In this mode, a Spring * bean factory is able to host components that expect constructor-based * dependency resolution. * @param beanName the name of the bean * @param mbd the bean definition for the bean * @param ctors the chosen candidate constructors * @param explicitArgs argument values passed in programmatically via the getBean method, * or {@code null} if none (-> use constructor argument values from bean definition) * @return BeanWrapper for the new instance */ protected BeanWrapper autowireConstructor( String beanName, RootBeanDefinition mbd, Constructor<?>[] ctors, Object[] explicitArgs) { return new ConstructorResolver(this).autowireConstructor(beanName, mbd, ctors, explicitArgs); }
构造方法注入实例化对象,到这里就不再谈了,有兴趣可以自己看源码,内容比较复杂,这里进行了构造方法的排序,筛选,决策要使用构造方法等。我们常用的都是set方法注入,所以跳过这里,直接去看另一种情况。
直接实例化Bean:
/** * 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 { 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); } }这里通过CglibSubclassingInstantiationStrategy类的instantiate方法创建对象实例,然后使用BeanWrapperImpl对象进行包装,初始化后返回。
相关文章推荐
- Spring mvc 框架下实现页面过期时,登录后返回原页面
- (java)Plus One
- 新手用eclipse运行web工程时经常会遇到的一个问题
- 解析Java的Spring框架的BeanPostProcessor发布处理器
- (java)House Robber
- java BigDecimal介绍
- 安卓JNI--JNI底层C回调Java方法
- JAVA通信编程(四)——UDP通讯
- JAVA通信编程(四)——UDP通讯
- Java的Spring框架中bean的继承与内部bean的注入
- 《疯狂JAVA讲义》——Singleton类
- Java对象创建之new关键字和newinstance()方法
- AES算法 Java实现
- maven 3.3.3 + MyEclipse2015 for windows 配置
- Java内存管理机制
- JAVA JTextField 和JTextArea的一般方法
- Java类-Stack的学习
- 转载:Java使用dom4j解析XML
- JAVA读取文件中存在BOM的问题
- c#调用JAVA提供的WebService处理日期格式