spring系列-注解驱动原理及源码-bean生命周期
目錄
一、Bean的初始化和銷毀
1、@Bean指定初始化和銷毀方法
2、通過實現InitializingBean和Disposabean來初始化和銷毀bean
3、使用JSR250定義的@PostConstruct&@PreDestroy注解來創建和銷毀bean
4、BeanPostProcessor-后置處理器(全局)
5、生命周期總結
二、BeanPostProcessor原理
1、BeanPostProcessor原理
2、spring底層對BeanPostProcessor的使用
一、Bean的初始化和銷毀
1、@Bean指定初始化和銷毀方法
(1)定義bean類
package com.xiang.spring.bean;public class Car {public Car() {System.out.println("car constructor ...");}public void init() {System.out.println("car init ...");}public void destory() {System.out.println("car destory ...");} }(2)編寫配置類
package com.xiang.spring.config;import com.xiang.spring.bean.Car; import org.springframework.context.annotation.Bean; import org.springframework.context.annotation.Configuration; import org.springframework.context.annotation.Scope;/** * bean的生命周期(由容器管理): * bean創建——初始化——銷毀 * 可以自定義初始化和銷毀方法,容器在bean進行到當前生命周期的時候來調用我們自定義的初始化和銷毀方法。 * * 構造(創建對象): * 單實例:在容器啟動的時候創建對象 * 多實例:在每次獲取的時候創建對象 * 初始化: * 對象創建完成,并賦值好,調用初始化方法。 * 銷毀: * 單實例bean:在容器關閉時進行銷毀。 * 多實例bean:容器不會管理bean,容器不會調用銷毀方法。 * * 1、指定初始化和銷毀方法: * 通過@Bean指定init-method和destroy-method * */ @Configuration public class MainConfigOfLifeCycle {//@Scope("prototype")@Bean(initMethod = "init", destroyMethod = "destory")public Car car() {return new Car();} }(3)測試程序
@Test public void test01() {// 創建ioc容器,容器創建時,默認會將單例的bean都創建出來AnnotationConfigApplicationContext applicationContext = new AnnotationConfigApplicationContext(MainConfigOfLifeCycle.class);System.out.println("容器創建完成");applicationContext.getBean("car");// 容器關閉 就會銷毀beanapplicationContext.close(); }//執行結果 car constructor ... car init ... 容器創建完成 car destory ...2、通過實現InitializingBean和Disposabean來初始化和銷毀bean
(1)定義bean類
package com.xiang.spring.bean;import org.springframework.beans.factory.DisposableBean; import org.springframework.beans.factory.InitializingBean;public class Cat implements InitializingBean, DisposableBean {public Cat() {System.out.println("cat construator");}// 銷毀public void destroy() throws Exception {System.out.println("cat destroy");}// 初始化public void afterPropertiesSet() throws Exception {System.out.println("cat init");} }(2)配置類
@Bean public Cat cat() {return new Cat(); }(3)測試類
@Test public void test01() {// 創建ioc容器,容器創建時,默認會將單例的bean都創建出來AnnotationConfigApplicationContext applicationContext = new AnnotationConfigApplicationContext(MainConfigOfLifeCycle.class);System.out.println("容器創建完成");// 容器關閉 就會銷毀beanapplicationContext.close(); }// 運行結果 cat construator cat init 容器創建完成 cat destroy3、使用JSR250定義的@PostConstruct&@PreDestroy注解來創建和銷毀bean
(1)定義bean
package com.xiang.spring.bean;import org.springframework.stereotype.Component;import javax.annotation.PostConstruct; import javax.annotation.PreDestroy;@Component public class Dog {public Dog() {System.out.println("dog constructor ...");}// 對象創建并賦值之后調用@PostConstructpublic void init() {System.out.println("dog PostConstruct ...");}// 容器移除對象之前調用@PreDestroypublic void destory() {System.out.println("dog PreDestroy ...");} }(2)測試查看結果
@Test public void test01() {// 創建ioc容器,容器創建時,默認會將單例的bean都創建出來AnnotationConfigApplicationContext applicationContext = new AnnotationConfigApplicationContext(MainConfigOfLifeCycle.class);System.out.println("容器創建完成");// 容器關閉 就會銷毀beanapplicationContext.close(); }dog constructor ... dog PostConstruct ... 容器創建完成 dog PreDestroy ...4、BeanPostProcessor-后置處理器(全局)
(1)編寫自定義BeanPostProcessor
package com.xiang.spring.bean;import org.springframework.beans.BeansException; import org.springframework.beans.factory.config.BeanPostProcessor; import org.springframework.stereotype.Component;/** * 后置處理器:初始化前后進行工作 * 方法返回值:包裝好的bean */ //@Component public class MyBeanPostProcessor implements BeanPostProcessor {public Object postProcessBeforeInitialization(Object bean, String beanName) throws BeansException {System.out.println(beanName + " - MyBeanPostProcessor - postProcessBeforeInitialization");return bean;}public Object postProcessAfterInitialization(Object bean, String beanName) throws BeansException {System.out.println(beanName + "MyBeanPostProcessor - postProcessAfterInitialization");return bean;} }(2)測試查看結果
可以看出來,所有的bean都在初始化前后執行了postProcessBeforeInitialization和postProcessAfterInitialization。
@Test public void test01() {// 創建ioc容器,容器創建時,默認會將單例的bean都創建出來AnnotationConfigApplicationContext applicationContext = new AnnotationConfigApplicationContext(MainConfigOfLifeCycle.class);System.out.println("容器創建完成");// 容器關閉 就會銷毀beanapplicationContext.close(); }// 運行結果 org.springframework.context.event.internalEventListenerProcessor - MyBeanPostProcessor - postProcessBeforeInitialization org.springframework.context.event.internalEventListenerProcessorMyBeanPostProcessor - postProcessAfterInitialization org.springframework.context.event.internalEventListenerFactory - MyBeanPostProcessor - postProcessBeforeInitialization org.springframework.context.event.internalEventListenerFactoryMyBeanPostProcessor - postProcessAfterInitialization mainConfigOfLifeCycle - MyBeanPostProcessor - postProcessBeforeInitialization mainConfigOfLifeCycleMyBeanPostProcessor - postProcessAfterInitialization dog constructor ... dog - MyBeanPostProcessor - postProcessBeforeInitialization dog PostConstruct ... dogMyBeanPostProcessor - postProcessAfterInitialization car constructor ... car - MyBeanPostProcessor - postProcessBeforeInitialization car init ... carMyBeanPostProcessor - postProcessAfterInitialization cat construator cat - MyBeanPostProcessor - postProcessBeforeInitialization cat init catMyBeanPostProcessor - postProcessAfterInitialization 容器創建完成 cat destroy car destory ... dog PreDestroy ...5、生命周期總結
bean的生命周期(由容器管理):
?????bean創建——初始化——銷毀
可以自定義初始化和銷毀方法,容器在bean進行到當前生命周期的時候來調用我們自定義的初始化和銷毀方法。
構造(創建對象):
?????單實例:在容器啟動的時候創建對象
?????多實例:在每次獲取的時候創建對象
初始化:
?????對象創建完成,并賦值好,調用初始化方法。
銷毀:
?????單實例bean:在容器關閉時進行銷毀。
?????多實例bean:容器不會管理bean,容器不會調用銷毀方法。
① 、指定初始化和銷毀方法:
?????通過@Bean指定init-method和destroy-method
② 、通過讓bean實現InitializingBean(定義初始化邏輯)
?????實現DisposableBean(定義銷毀邏輯)
③ 、可以使用JSR250:
?????@PostConstruct:在bean創建完成并且屬性賦值完成后,來執行初始化
?????@PreDestroy:在容器銷毀bean之前,通知我們進行清理工作
④ 、BeanPostProcessor接口:bean的后置處理器:
?????在bean初始化前后進行一些處理工作。
?????postProcessBeforeInitialization:在初始化之前工作
?????postProcessAfterInitialization:在初始化之后工作
二、BeanPostProcessor原理
1、BeanPostProcessor原理
? ? 遍歷得到容器中所有的BeanPostProcessor,挨個執行beforeInitialization,一旦返回null,跳出for循環,不會執行后面的BeanPostProcessor。
?? ?源碼中是先執行populateBean方法進行屬性賦值、再執行postProcessBeforeInitialization方法,再執行初始化方法、再執行postProcessAfterInitialization方法。
/** * 初始化bean的完整源碼 */ protected Object initializeBean(final String beanName, final Object bean, RootBeanDefinition mbd) {if (System.getSecurityManager() != null) {AccessController.doPrivileged(new PrivilegedAction<Object>() {@Overridepublic Object run() {invokeAwareMethods(beanName, bean);return null;}}, getAccessControlContext());}else {invokeAwareMethods(beanName, bean);}Object wrappedBean = bean;if (mbd == null || !mbd.isSynthetic()) {wrappedBean = applyBeanPostProcessorsBeforeInitialization(wrappedBean, beanName);}try {invokeInitMethods(beanName, wrappedBean, mbd);}catch (Throwable ex) {throw new BeanCreationException((mbd != null ? mbd.getResourceDescription() : null),beanName, "Invocation of init method failed", ex);}if (mbd == null || !mbd.isSynthetic()) {wrappedBean = applyBeanPostProcessorsAfterInitialization(wrappedBean, beanName);}return wrappedBean; }2、spring底層對BeanPostProcessor的使用
bean賦值,注入其他組件、@Autowired、生命周期注解功能、@Async、等等很多功能都用到了BeanPostProcessor。
?
?
總結
以上是生活随笔為你收集整理的spring系列-注解驱动原理及源码-bean生命周期的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: spring系列-注解驱动原理及源码-b
- 下一篇: spring系列-注解驱动原理及源码-属