beanfactory中單例bean的初始化過程(一)
阿新 • • 發佈:2019-11-01
Date 10.06 pm
Point
完成beanfactory中單例bean的初始化
beanFactory.preInstantiateSingletons()
- 拿到所有的bean定義資訊(在
beanDefinitionNames
中,遍歷list - 獲取到bean的定義資訊
- 如果這個bean不是抽象,是單例,不是懶載入的
判斷這個bean是否factorybean(判斷這個bean有沒有實現factoryBean介面),是的話,用工廠裡面的方法去建立bean。
- 呼叫
getbean(&beanname)
獲取到beanFactory物件。
- 呼叫
- 呼叫
getBean(beanName)
- 呼叫
doGetBean()
transformedBeanName
進入這個方法將之前工廠bean的字首去除,將別名轉成正式的名稱getSingleton
檢測單例快取中是否有已構建的單例項bean,有就直接返回這個單例bean
所有例項過的單例bean都會在這注冊,檢查的時候還會判斷當前bean有沒有在建立過程中。如果有的話,會在/** Cache of singleton objects: bean name to bean instance. */ private final Map<String, Object> singletonObjects = new ConcurrentHashMap<>(256);
earlySingletonObjects
singletonFactories
這個map中去獲取,要是獲取到的話就刪除singletonFactories
中的bean,轉而在earlySingletonObjects
這個map裡面去註冊- 沒有獲取到bean(開始建立bean的流程)
- 就先判斷下我們是不是正在建立這個bean的例項,避免迴圈引用的問題。
- 獲取bean的父工廠(這個主要是如果有Springmvc的話 可能會有這種父子工廠)這個父工廠要是能獲取到的話,又會去呼叫父工廠的dogetbean方法,獲取不到父工廠的話直接下一步
- 標記當前bean已經建立,大概就是把當前beanname放到
Collections.newSetFromMap(new ConcurrentHashMap<>(256))
- 獲取bean的定義資訊
- 獲取bean所依賴的其他bean,如果有,還是呼叫getbean的方式去構建那些依賴的bean
- 如果這個bean是單例bean,回掉
createBean
,開始單例bean建立- 拿到bean的定義資訊
- 解析bean的定義的型別,檢查這個定義資訊中的beanClass是不是為空
- 檢測是否有bean方法被重寫,有的話準備重寫這個bean方法(也是檢查bean定義資訊裡面的
methodOverrides
這個屬性有沒有值) - 讓BeanPostProcessor提前攔截,返回代理物件
resolveBeforeInstantiation()
- 先根據定義資訊中的
beforeInstantiationResolved
判斷初始化之前有沒有處理,有的話就不進入這個processor中了, - 然後判斷這個值是不是由application定義的 和 判斷當前factory中已經有了
InstantiationAwareBeanPostProcessor
這個processor了,然後去獲取這個bean的目標class,然後呼叫InstantiationAwareBeanPostProcessor.postProcessBeforeInstantiation
啟動前置處理器,然後如果返回的bean有值的話,再呼叫applyBeanPostProcessorsAfterInitialization
後置處理器,然後將bean定義資訊中beforeInstantiationResolved
這個引數賦值成這個返回的bean,然後返回這個bean
- 先根據定義資訊中的
- 呼叫
https://github.com/fulln