spring IoC容器構造bean過程簡單分析

Spring構造bean和管理初始化生命週期的工作在AbstractAutowireCapableBeanFactory中處理,分爲構造bean和後續管理bean初始化生命週期。

1.  構造bean

1.1方法調用圖

構造bean的入口就是beanFactory的getBean()方法,實際調用defaultBeanFactory的getBean()方法。經過層層調用,直到AabstractAutowireCapableBeanFactory中。調用方法圖如下:


3-6均在AbstractAutowireCapableBeanFactory完成。

1.2設計到的類圖

涉及的類圖繼承關係如下:

在doCreateBean()中,createBeanInstance返回的是一個BeanWrapper

BeanWrapper提供了設置和獲取屬性值(單個的或者是批量的),獲取屬性描述信息、查詢只讀或者可寫屬性等功能,用getWrappedInstance()方法就可以得到這個封裝的bean的實例。BeanWrapperImpl裏面的Object就是BeanWrapper“包裹”的bean,通過getWrappedInstance()方法對外提供。

1.3方法分析

主要分析AbstractAutowireCapableBeanFactory中的方法,其它類中的方法都是對這裏方法的封裝。

A,BeanWrapper的獲取

BeanWrapper提供了設置和獲取屬性值(單個的或者是批量的),獲取屬性描述信息、查詢只讀或者可寫屬性等功能,用getWrappedInstance()方法就可以得到這個封裝的bean的實例。BeanWrapperImpl裏面的Object就是BeanWrapper“包裹”的bean,通過getWrappedInstance()方法對外提供。

/**
      * Return the bean instance wrapped by this object, if any.
      * @return the bean instance, or <code>null</code> if none set
      */
      Object getWrappedInstance();

BeanWrapper的獲取由createBeanInstance()得到。在doCreateBean()中調用createBeanInstance(),返回BeanWrapper。

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

B. createBeanInstance()實現分析

createBeanInstance()中得到了BeanWrapper,該方法調用instantiateBean()。instantiateBean()方法申明如下:

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

createBeanInstance()中得到BeanWrapper的代碼如下:

beanInstance =   getInstantiationStrategy().instantiate(mbd, beanName, parent);  //      這裏構造出需要的bean
BeanWrapper bw = new BeanWrapperImpl(beanInstance);   //將這個bean放入對應的beanWrapper

getInstantiationStrategy()返回CglibSubclassingInstantiationStrategy,因爲在AbstractAutowireCapableBeanFactory初始化的時候,就做了

private InstantiationStrategy instantiationStrategy = new CglibSubclassingInstantiationStrategy();

故Spring構造bean對象默認使用cglib庫,而不是使用jdk中的反射。

C. instantiate()實現

CglibSubclassingInstantiationStrategy中實現instantiate()方法,如下:

public Object instantiate(Constructor ctor, Object[] args) {
                 Enhancer enhancer = new Enhancer();
      enhancer.setSuperclass(this.beanDefinition.getBeanClass());
                 enhancer.setCallbackFilter(new CallbackFilterImpl());
                 enhancer.setCallbacks(new Callback[] {
                            NoOp.INSTANCE,
                            new LookupOverrideMethodInterceptor(),
                            new ReplaceOverrideMethodInterceptor()
                 });
                 return (ctor == null) ? 
                            enhancer.create() : 
                            enhancer.create(ctor.getParameterTypes(), args);
           }

這裏是調用cglib庫,來構造對象,也是很標準的使用cglib庫構造對象的調用。

2. 後續工作

後續工作主要完成bean生命週期相關的管理。


Spring生命週期概述1

1)設置屬性值;

2)調用Bean中的BeanNameAware.setBeanName()方法,如果該Bean實現了BeanNameAware接口;

3)調用Bean中的BeanFactoryAware.setBeanFactory()方法,如果該Bean實現了BeanFactoryAware接口;

4)調用BeanPostProcessors.postProcessBeforeInitialization()方法;

5)調用Bean中的afterPropertiesSet方法,如果該Bean實現了InitializingBean接口;

6)調用Bean中的init-method,通常是在配置bean的時候指定了init-method,例如:<beanclass="beanClass"init-method="init"></bean>

7)調用BeanPostProcessors.postProcessAfterInitialization()方法;

8)如果該Bean是單例的,則當容器銷燬並且該Bean實現了DisposableBean接口的時候,調用destory方法;如果該Bean是prototype,則將準備好的Bean提交給調用者,後續不再管理該Bean的生命週期。

 initializeBean()方法在AbstractAutowireCapableBeanFactory中,對應Bean生命週期的2-7。initializeBean()在doCreateBean()中調用createBeanInstance()之後。調用了4個方法:

invokeAwareMethods(對應生命週期2、3)

applyBeanPostProcessorsBeforeInitialization(對應生命週期4)

invokeInitMethods(對應生命週期5,6)

applyBeanPostProcessorsAfterInitialization(對應生命週期7)

2.1 invokeAwareMethods

invokeAwareMethods調用bean自省的三個方法(如果該bean實現BeanNameAware接口、BeanClassLoaderAware接口、BeanFactoryAware接口)

private void invokeAwareMethods(final String beanName, final Object bean) {
           if (bean instanceof Aware) {
                 if (bean instanceof BeanNameAware) {
                      ((BeanNameAware) bean).setBeanName(beanName);
                 }
                 if (bean instanceof BeanClassLoaderAware) {
                      ((BeanClassLoaderAware) bean).setBeanClassLoader(getBeanClassLoader());
                 }
                 if (bean instanceof BeanFactoryAware) {
                      ((BeanFactoryAware) bean).setBeanFactory(AbstractAutowireCapableBeanFactory.this);
                 }
           }
      }

2.2applyBeanPostProcessorsBeforeInitialization

完成前置處理,即調用postProcessBeforeInitialization()方法,在Bean初始化動作之前完成特定的需求。

public Object applyBeanPostProcessorsBeforeInitialization(Object existingBean, String beanName)
                 throws BeansException {
           Object result = existingBean;
           for (BeanPostProcessor beanProcessor : getBeanPostProcessors()) {
                 result = beanProcessor.postProcessBeforeInitialization(result, beanName);
                 if (result == null) {
                      return result;
                 }
           }
           return result;
      }

2.3 invokeInitMethods

調用afterPropertiesSet()方法;如果配置bean的時候指定了init-method,那麼調用invokeCustomInitMethod

boolean isInitializingBean = (bean instanceof InitializingBean);
……
((InitializingBean) bean).afterPropertiesSet(); 
 //調用afterPropertiesSet()方法
invokeCustomInitMethod();           //調用指定的init-method

2.4 applyBeanPostProcessorsAfterInitialization

實現和postProcessBeforeInitialization類似,完成bean初始化後的後置處理。只是在postProcessBeforeInitialization()的for循環中改爲:

result =beanProcessor.postProcessAfterInitialization(result, beanName);

3.其它

     感覺spring構造bean的和管理bean對象生命週期的實現,比之前spring IoC容器的初始化的過程要簡單,也好理解。

4. 參考資料

1.   http://sexycoding.iteye.com/blog/1046775:也談Spring Bean的生命週期

2.  參考書籍《Spring 技術內幕—深入解析Spring架構與設計原理》第二章





發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章