導讀
- Spring中Bean的生命周期從容器的啟動到停止,涉及到的源碼主要是在
方法中,下面也是圍繞其中的邏輯進行講解。org.springframework.context.support.AbstractApplicationContext.refresh
開撸
【1】 prepareRefresh()
内部其實很簡單,就是設定一些标志,比如開始時間,激活的狀态等。
【2】prepareBeanFactory(beanFactory)
做一些簡單的準備工作,此處不再贅述!!!
【3】postProcessBeanFactory(beanFactory)
主要的作用就是添加了一個後置處理器
ServletContextAwareProcessor
【4】invokeBeanFactoryPostProcessors(beanFactory)
調用容器中的所有的BeanFactoryPostProcessor中的postProcessBeanFactory方法,按照優先級調用,主要實作邏輯在org.springframework.context.support.PostProcessorRegistrationDelegate.invokeBeanFactoryPostProcessors(org.springframework.beans.factory.config.ConfigurableListableBeanFactory, java.util.List<org.springframework.beans.factory.config.BeanFactoryPostProcessor>)
(1) 執行所有BeanDefinitionRegistryPostProcessor(對BeanFactoryPostProcessor的擴充,運作在普通的實作類之前注冊bean)的方法,同樣是内部按照優先級進行排序調用
(2) 對剩餘的進行按照優先級排序調用,同樣是内部進行排序執行
【5】registerBeanPostProcessors(beanFactory)
注冊所有的BeanPostProcessor(後置處理器),按照優先級注冊,分别是PriorityOrdered,Ordered,普通的,内部的。主要的實作邏輯在PostProcessorRegistrationDelegate.registerBeanPostProcessors()
【6】initMessageSource()
注冊MessageSource,提供消息國際化等功能
【7】initApplicationEventMulticaster();
注冊事件廣播器ApplicationEventMulticaster,用于spring事件的廣播和事件監聽器的處理
【8】registerListeners()
注冊事件監聽器ApplicationListener,并且廣播一些早期的事件,主要的邏輯在org.springframework.context.support.AbstractApplicationContext.registerListeners
【9】finishBeanFactoryInitialization(beanFactory)
執行個體化所有非懶加載的Bean,spring生命周期中的主要方法,主要邏輯在org.springframework.beans.factory.support.DefaultListableBeanFactory.preInstantiateSingletons,深入進去其實就是getBean()方法建立,詳情向下看。
【10】finishRefresh()
主要的功能是釋出事件ContextRefreshedEvent
【11】destroyBeans()
容器啟動出現異常時銷毀Bean
以上就是Spring容器啟動的過程,主要的邏輯都在org.springframework.context.support.AbstractApplicationContext#refresh中,其他的都很容易了解,現在我們着重分析一下單例Bean的建立過程,入口是第9步。
執行個體化單例Bean
【1】debug進入,實際主要的邏輯都在org.springframework.beans.factory.support.DefaultListableBeanFactory#preInstantiateSingletons方法中,邏輯如下:
//擷取所有注入到ioc容器中的bean定義資訊
List<String> beanNames = new ArrayList<>(this.beanDefinitionNames);
//循環建立
for (String beanName : beanNames) {
RootBeanDefinition bd = getMergedLocalBeanDefinition(beanName);
//非抽象,單例,非懶加載的bean初始化
if (!bd.isAbstract() && bd.isSingleton() && !bd.isLazyInit()) {
//如果是FactoryBean
if (isFactoryBean(beanName)) {
//getBean
Object bean = getBean(FACTORY_BEAN_PREFIX + beanName);
//非FactoryBean,getBean
else {
getBean(beanName);
}
}
}
以上源碼總結得知,最終執行個體化Bean的方法肯定在getBean中的,debug進入,得知doGetBean是大boss,spring源碼有趣的是最終的實作都是在doxxxx()。
【2】AbstractBeanFactory#doGetBean,由于篇幅太短,就不貼源碼了,隻貼關鍵代碼
執行個體化的主要流程全部都在這裡,下面一一解析即可。
(1) Object sharedInstance = getSingleton(beanName)
從早期的緩存中擷取,如果存在傳回Bean,執行個體化
(2)BeanFactory parentBeanFactory = getParentBeanFactory()
從父工廠的中擷取Bean
(3)if (mbd.isSingleton())
分單例和多例進行分開建立Bean,這裡隻分析單例Bean的建立
(4)sharedInstance = getSingleton(beanName, () -> { try { return createBean(beanName, mbd, args); }
createBean方法建立Bean,進入createBean()
a. Object bean = resolveBeforeInstantiation(beanName, mbdToUse):執行所有的InstantiationAwareBeanPostProcessor中的postProcessBeforeInstantiation,在執行個體化之前調用,傳回null繼續下一步,傳回一個bean,那麼bean執行個體化完成,将調用其中的postProcessAfterInstantiation方法
b. Object beanInstance = doCreateBean(beanName, mbdToUse, args):建立Bean的完成過程
c. 進入doCreateBean,instanceWrapper = createBeanInstance(beanName, mbd, args):建立Bean的執行個體
d. populateBean(beanName, mbd, instanceWrapper):屬性裝配,執行InstantiationAwareBeanPostProcessor的postProcessAfterInstantiation,再執行postProcessProperties方法。
e. exposedObject = initializeBean(beanName, exposedObject, mbd):初始化Bean,debug進入
f. invokeAwareMethods(beanName, bean):調用BeanNameAware,BeanClassLoaderAware,BeanFactoryAware中的對應方法
g. wrappedBean = applyBeanPostProcessorsBeforeInitialization(wrappedBean, beanName):調用BeanPostProcessord中的postProcessBeforeInitialization方法
h. invokeInitMethods(beanName, wrappedBean, mbd):執行InitializingBean中的afterPropertiesSet
i. wrappedBean = applyBeanPostProcessorsAfterInitialization(wrappedBean, beanName):調用BeanPostProcessor中的postProcessAfterInitialization方法
總結
以上是spring容器從啟動到銷毀的全部過程,根據源碼陳某畫了一張生命周期的圖,僅供參考,請勿轉載!!!
- 如果覺得作者寫的好,有所收獲的話,點個關注推薦一下喲!!!
如果覺得作者寫的好,有所收獲的話,點個關注,推薦一波,文章首發于公衆号!!!