基础框架 Spring Bean的生命周期
一、生命周期流程图:
Spring Bean的完整生命周期从创建Spring容器开始,直到最终Spring容器销毁Bean,这其中包含了一系列关键点。
二、各种接口方法分类
Bean的完整生命周期经历了各种方法调用,这些方法可以划分为以下几类:
1、Bean自身的方法:这个包括了Bean本身调用的方法和通过配置文件中的init-method和destroy-method指定的方法
2、Bean级生命周期接口方法:这个包括了BeanNameAware、BeanFactoryAware、InitializingBean和DiposableBean这些接口的方法
3、容器级生命周期接口方法:这个包括了InstantiationAwareBeanPostProcessor 和 BeanPostProcessor 这两个接口实现,一般称它们的实现类为“后处理器”。
4、工厂后处理器接口方法:这个包括了AspectJWeavingEnabler, ConfigurationClassPostProcessor, CustomAutowireConfigurer等等非常有用的工厂后处理器 接口的方法。工厂后处理器也是容器级的。在应用上下文装配配置文件之后立即调用。
三、验证
package com.spring5.beanlife;
import org.springframework.beans.BeansException;
import org.springframework.beans.factory.*;
/**
* 用户类
* 验证bean生命周期
*
* 1、首先是一个简单的Spring Bean,调用Bean自身的方法和Bean级生命周期接口方法,为了方便演示,
* 它实现了BeanNameAware、BeanFactoryAware、InitializingBean和DiposableBean这4个接口,同时有2个方法,
* 对应配置文件中<bean>的init-method和destroy-method。如下:
*
* @author zrj
* @date 2020/12/19
* @since V1.0
**/
public class User implements BeanFactoryAware, BeanNameAware,
InitializingBean, DisposableBean {
private String name;
private String address;
private String phone;
private BeanFactory beanFactory;
private String beanName;
public User() {
System.out.println( "---------【构造器】调用User的构造器实例化---------" );
}
public User(String name, String address, String phone) {
System.out.println( "【构造器-有参】调用User的构造器实例化" );
this.name = name;
this.address = address;
this.phone = phone;
}
public String getName() {
return name;
}
public void setName(String name) {
System.out.println( "【注入属性】注入属性name" );
this.name = name;
}
public String getAddress() {
return address;
}
public void setAddress(String address) {
System.out.println( "【注入属性】注入属性address" );
this.address = address;
}
public String getPhone() {
return phone;
}
public void setPhone(String phone) {
System.out.println( "【注入属性】注入属性phone" );
this.phone = phone;
}
@Override
public String toString() {
return "User{" +
"name='" + name + '\'' +
", address='" + address + '\'' +
", phone='" + phone + '\'' +
'}';
}
/**
* 实现BeanFactoryAware接口
*/
@Override
public void setBeanFactory(BeanFactory beanFactory) throws BeansException {
System.out.println( "【BeanFactoryAware接口】调用BeanFactoryAware.setBeanFactory()" );
this.beanFactory = beanFactory;
}
/**
* 实现BBeanNameAware接口
*/
@Override
public void setBeanName(String s) {
System.out.println( "【BeanNameAware接口】调用BeanNameAware.setBeanName()" );
this.beanName = s;
}
/**
* 实现InitializingBean接口
*/
@Override
public void afterPropertiesSet() throws Exception {
System.out.println( "【InitializingBean接口】调用InitializingBean.afterPropertiesSet()" );
}
/**
* 实现DisposableBean接口
*/
@Override
public void destroy() throws Exception {
System.out.println( "【DiposibleBean接口】调用DiposibleBean.destory()" );
}
/**
* 通过<bean>的init-method属性指定的初始化方法
*/
public void myInit() {
System.out.println( "【init-method】调用<bean>的init-method属性指定的初始化方法" );
}
/**
* 通过<bean>的destroy-method属性指定的初始化方法
*/
public void myDestory() {
System.out.println( "【destroy-method】调用<bean>的destroy-method属性指定的初始化方法" );
}
}
package com.spring5.beanlife;
import org.springframework.beans.BeansException;
import org.springframework.beans.factory.config.BeanPostProcessor;
/**
* 2、接下来是演示BeanPostProcessor接口的方法,如下:
*
* @author zrj
* @date 2020/12/19
* @since V1.0
**/
public class MyBeanPostProcessor implements BeanPostProcessor {
public MyBeanPostProcessor() {
super();
System.out.println( "【构造器】这是BeanPostProcessor实现类构造器" );
}
@Override
public Object postProcessAfterInitialization(Object arg0, String arg1) throws BeansException {
System.out.println( "【BeanPostProcessor】接口方法postProcessAfterInitialization对属性进行更改!!!" );
return arg0;
}
@Override
public Object postProcessBeforeInitialization(Object arg0, String arg1) throws BeansException {
System.out.println( "【BeanPostProcessor】接口方法postProcessBeforeInitialization对属性进行更改!" );
return arg0;
}
}
package com.spring5.beanlife;
import org.springframework.beans.BeansException;
import org.springframework.beans.PropertyValues;
import org.springframework.beans.factory.config.InstantiationAwareBeanPostProcessorAdapter;
import java.beans.PropertyDescriptor;
/**
* 3、InstantiationAwareBeanPostProcessor 接口本质是BeanPostProcessor的子接口,
* 一般我们继承Spring为其提供的适配器类InstantiationAwareBeanPostProcessor Adapter来使用它,如下:
* <p>
* 这个有3个方法,其中第二个方法postProcessAfterInitialization就是重写了BeanPostProcessor的方法。
* 第三个方法postProcessPropertyValues用来操作属性,返回值也应该是PropertyValues对象。
*
* @author zrj
* @date 2020/12/19
* @since V1.0
**/
public class MyInstantiationAwareBeanPostProcessor extends InstantiationAwareBeanPostProcessorAdapter {
/**
* 构造方法
*/
public MyInstantiationAwareBeanPostProcessor() {
super();
System.out.println( "【构造器】这是InstantiationAwareBeanPostProcessorAdapter实现类构造器!!!" );
}
/**
* 接口方法、实例化Bean之前调用
*/
@Override
public Object postProcessBeforeInstantiation(Class beanClass, String beanName) throws BeansException {
System.out.println( "【InstantiationAwareBeanPostProcessor】调用postProcessBeforeInstantiation方法" );
return null;
}
/**
* 接口方法、实例化Bean之后调用
*/
@Override
public Object postProcessAfterInitialization(Object bean, String beanName) throws BeansException {
System.out.println( "【InstantiationAwareBeanPostProcessor】调用postProcessAfterInitialization方法" );
return bean;
}
/**
* 接口方法、设置某个属性时调用
*/
@Override
public PropertyValues postProcessPropertyValues(PropertyValues pvs, PropertyDescriptor[] pds, Object bean, String beanName) throws BeansException {
System.out.println( "【InstantiationAwareBeanPostProcessor】调用postProcessPropertyValues方法" );
return pvs;
}
}
package com.spring5.beanlife;
import org.springframework.beans.BeansException;
import org.springframework.beans.factory.config.BeanDefinition;
import org.springframework.beans.factory.config.BeanFactoryPostProcessor;
import org.springframework.beans.factory.config.ConfigurableListableBeanFactory;
/**
* 4、演示工厂后处理器接口方法,如下
*
* @author zrj
* @date 2020/12/19
* @since V1.0
**/
public class MyBeanFactoryPostProcessor implements BeanFactoryPostProcessor {
public MyBeanFactoryPostProcessor() {
super();
System.out.println( "【构造器】这是BeanFactoryPostProcessor实现类构造器!!!" );
}
@Override
public void postProcessBeanFactory(ConfigurableListableBeanFactory arg0) throws BeansException {
System.out.println( "【BeanFactoryPostProcessor】调用postProcessBeanFactory方法" );
BeanDefinition bd = arg0.getBeanDefinition( "user" );
bd.getPropertyValues().addPropertyValue( "name", "菜鸟" );
}
}
package com.spring5.beanlife;
import org.springframework.context.ApplicationContext;
import org.springframework.context.support.ClassPathXmlApplicationContext;
/**
* bean生命周期测试类
*
* @author zrj
* @date 2020/12/19
* @since V1.0
**/
public class BeanLifeCycle {
public static void main(String[] args) {
System.out.println( "----------初始化容器开始----------" );
ApplicationContext context = new ClassPathXmlApplicationContext( "bean1.xml" );
System.out.println( "----------初始化容器结束----------" );
// 获取User对象
User user = context.getBean( "user", User.class );
System.out.println( "【user对象】:" + user );
System.out.println( "----------现在开始关闭容器----------" );
((ClassPathXmlApplicationContext) context).registerShutdownHook();
}
}
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:p="http://www.springframework.org/schema/p"
xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd">
<bean id="beanPostProcessor" class="com.spring5.beanlife.MyBeanPostProcessor"></bean>
<bean id="instantiationAwareBeanPostProcessor"
class="com.spring5.beanlife.MyInstantiationAwareBeanPostProcessor"></bean>
<bean id="beanFactoryPostProcessor" class="com.spring5.beanlife.MyBeanFactoryPostProcessor"></bean>
<bean id="user" class="com.spring5.beanlife.User" init-method="myInit" destroy-method="myDestory" scope="singleton">
<property name="name" value="jerry"></property>
<property name="address" value="悉尼"></property>
<property name="phone" value="123456"></property>
</bean>
</beans>
执行结果
----------初始化容器开始----------
【构造器】这是BeanFactoryPostProcessor实现类构造器!!!
【BeanFactoryPostProcessor】调用postProcessBeanFactory方法
【构造器】这是BeanPostProcessor实现类构造器
【构造器】这是InstantiationAwareBeanPostProcessorAdapter实现类构造器!!!
【InstantiationAwareBeanPostProcessor】调用postProcessBeforeInstantiation方法
---------【构造器】调用User的构造器实例化---------
【InstantiationAwareBeanPostProcessor】调用postProcessPropertyValues方法
【注入属性】注入属性name
【注入属性】注入属性address
【注入属性】注入属性phone
【BeanNameAware接口】调用BeanNameAware.setBeanName()
【BeanFactoryAware接口】调用BeanFactoryAware.setBeanFactory()
【BeanPostProcessor】接口方法postProcessBeforeInitialization对属性进行更改!
【InitializingBean接口】调用InitializingBean.afterPropertiesSet()
【init-method】调用<bean>的init-method属性指定的初始化方法
【BeanPostProcessor】接口方法postProcessAfterInitialization对属性进行更改!!!
【InstantiationAwareBeanPostProcessor】调用postProcessAfterInitialization方法
----------初始化容器结束----------
【user对象】:User{name='菜鸟', address='悉尼', phone='123456'}
----------现在开始关闭容器----------
【DiposibleBean接口】调用DiposibleBean.destory()
【destroy-method】调用<bean>的destroy-method属性指定的初始化方法
Process finished with exit code 0