Spring的生命周期

烈酒焚心 提交于 2020-02-13 11:33:26

1. 什么是Bean的生命周期

Bean的生命周期是指Bean创建–》初始化–》销毁的过程
我们可以自定义Bean的初始化和销毁方法
容器在bean进行到当前生命周期的时候,来调用自定义的初始化和销毁方法

2.生命周期–初始化与销毁1(正规军)

  1. 指定初始化init-method方法
  2. 指定销毁destory-method方法
    在这里插入图片描述
public class Bike {
    public Bike(){
        System.out.println("Bike constructor...............");
    }

    public void init(){
        System.out.println("Bike...........init.........");
    }
    public void destroy(){
        System.out.println("Bike....... destroy.........");
    }
}

单例:

@Configuration
public class Cap7MainConfig {
    @Bean
    public Person person(){
        System.out.println("给容器中添加person........");
        return new Person("person",20);
    }
    @Bean(initMethod = "init", destroyMethod = "destroy")
    public Bike bike(){
        return new Bike();
    }
}
public class Cap7Test {
    @Test
    public void test01() {
        AnnotationConfigApplicationContext app = new AnnotationConfigApplicationContext(Cap7MainConfig.class);
        System.out.println("IOC容器初始化完成");
        app.close();
    }
}

结果:
在这里插入图片描述

多例:

@Configuration
public class Cap7MainConfig {
    @Bean
    public Person person(){
        System.out.println("给容器中添加person........");
        return new Person("person",20);
    }
    @Scope("prototype")
    @Bean(initMethod = "init", destroyMethod = "destroy")
    public Bike bike(){
        return new Bike();
    }
}

结果:
在这里插入图片描述

  • 结论:
    单实例:在创建容器的同时,把对象实例化注册到容器中
    多实例和懒加载:创建容器的时候不会创建实例,只有在调用创建Bean的方法时候才会创建实例并注入到容器中

注:对于单实例的Bean, 可以正常调用初始化方法和销毁方法
对于多实例的Bean,容器只负责初始化,但不会管理bean,容器关闭时不会调用销毁方法

3. 生命周期—初始化与销毁2

  1. 实现InitalizingBean接口的afterPropertiesSet()方法,当BeanFactory创建好对象,且把bean所有属性,设置好之后会调用这个方法,相当于初始化方法
  2. 实现DisposableBean的destory()方法,当bean销毁时,会把单实例bean进行销毁
    在这里插入图片描述
  • Train.class
//采用组件扫描方式
@Component
public class Train implements InitializingBean, DisposableBean {
    public Train(){
        System.out.println("Train.......constructor.........");
    }
    //当bean销毁时,调用此方法
    @Override
    public void destroy() throws Exception {
        System.out.println("Train..........destroy..........");
    }
    //当bean属性赋值和初始化完成时调用
    @Override
    public void afterPropertiesSet() throws Exception {
        System.out.println("Train..........afterPropertiesSet()............");
    }
}
  • 配置
@Configuration
@ComponentScan(value = "cap7.bean")
public class Cap7MainConfig {

}
  • 测试
public class Cap7Test {
    @Test
    public void test01() {
        AnnotationConfigApplicationContext app = new AnnotationConfigApplicationContext(Cap7MainConfig.class);
        System.out.println("IOC容器初始化完成");
        app.close();
    }
}

结果:
在这里插入图片描述

4. 生命周期—初始化与销毁3

  • P可以使用JSR250规范定义的(java规范)两个注解来实现
    @PostConstruct: 在Bean创建完成,且属于赋值完成后进行初始化,属于JDK规范的注解
    @PreDestroy:在bean将被移除之前进行通知,在容器销毁之前进行清理工作

提示:JSR是由JDK提供的一组规范
在这里插入图片描述

  • Jeep.class
@Component
public class Jeep {
    public Jeep(){
        System.out.println("Jeep ............... Constructor..............");
    }

    @PostConstruct
    public void init(){
        System.out.println("Jeep.................PostConstruct............");
    }
    @PreDestroy
    public void destory(){
        System.out.println("Jeep...............PreDestroy...............");
    }
}
  • 结果:
  • 在这里插入图片描述

5. 生命周期-BeanPostProcessors

  • bean的后置处理器,在Bean初始化之前调用进行拦截,在bean初始化前后进行一些处理工作,使用BeanPostProcessors如何控制Bean的生命周期
  • 实现BeanPostProcessors的两个接口即可
  1. postProcessBeforeInitialization()
  2. postPeocessAfterInitialization()
@Component
public class WangBeanPostProcessor implements BeanPostProcessor {
    @Override
    public Object postProcessBeforeInitialization(Object bean, String beanName) throws BeansException {
    //返回一个对象(传过来的对象)
    //在初始化方法调用之前进行后置处理工作
    //什么时候调用它:init-method=init之前调用它
        System.out.println("postProcessBeforeInitialization     " + beanName + "  ....  " + bean);
        return bean;
    }

    @Override
    public Object postProcessAfterInitialization(Object bean, String beanName) throws BeansException {
        System.out.println("postProcessAfterInitialization     " + beanName + "...." + bean);
        return bean;
    }
}

在这里插入图片描述

6. 六种销毁创建同时定义的情况

public class Person implements InitializingBean, DisposableBean {

    public Person() {
        System.out.println("construct");
    }

    public void init() {
        System.out.println("init1");
    }

    public void close() {
        System.out.println("close1");
    }

    @Override
    public void destroy() throws Exception {
        // TODO Auto-generated method stub
        System.out.println("close 2");
    }

    @Override
    public void afterPropertiesSet() throws Exception {
        // TODO Auto-generated method stub
        System.out.println("init 2");
    }

    @PostConstruct
    public void myInit() throws Exception {
        // TODO Auto-generated method stub
        System.out.println("init 3");
    }

    @PreDestroy
    public void myDestroy() throws Exception {
        // TODO Auto-generated method stub
        System.out.println("close 3");
    }
}
@Component
public class PersonBeanPostProcessor implements BeanPostProcessor {
    @Override
    public Object postProcessBeforeInitialization(Object bean, String beanName) throws BeansException {
        System.out.println("postProcessBeforeInitialization     " + beanName + "  ....  " + bean);
        return bean;
    }

    @Override
    public Object postProcessAfterInitialization(Object bean, String beanName) throws BeansException {
        System.out.println("postProcessAfterInitialization     " + beanName + "...." + bean);
        return bean;
    }
}
@Configuration
@ComponentScan(value = "cap7.bean", includeFilters = {
        @ComponentScan.Filter(type = FilterType.ASSIGNABLE_TYPE, classes = {PersonBeanPostProcessor.class})
}, useDefaultFilters = false)
public class Cap7MainConfig {
    @Bean(initMethod = "init", destroyMethod = "close")
    public Person person(){
        System.out.println("给容器中添加person........");
        return new Person();
    }
////    @Scope("prototype")
//    @Bean(initMethod = "init", destroyMethod = "destroy")
//    public Bike bike(){
//        return new Bike();
//    }
}
public class Cap7Test {
    @Test
    public void test01() {
        AnnotationConfigApplicationContext app = new AnnotationConfigApplicationContext(Cap7MainConfig.class);
        System.out.println("IOC容器初始化完成");
        app.close();
    }
}

在这里插入图片描述
初始化和销毁顺序:

构造器之前的信息——》
	构造器中的信息——》
		postProcessBeforeInitialization【处理器】——》
			1. @PostConstruct【注解】——》
				2. afterPropertiesSet()【重写接口InitializingBean中的方法】——》
					3. initMethod = "init"——》
		postProcessAfterInitialization【处理器】 
---------------------------IOC容器初始化完成------------------------
			1. @PreDestroy【注解】——》
			 	2. destroy()【重写接口DisposableBean中的方法】——》
			 		3. destroyMethod = "close" ——》
			 		
易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!