spring的后置处理器——BeanPostProcessor以及spring的生命周期
后置处理器的调用时机
BeanPostProcessor是spring提供的接口,它有两个方法——postProcessBeforeInitialization、postProcessAfterInitialization。关于这两个方法的调用时机,可以参考spring源码注释。
/**
* Apply this BeanPostProcessor to the given new bean instance <i>before</i> any bean
* initialization callbacks (like InitializingBean's {@code afterPropertiesSet}
* or a custom init-method). The bean will already be populated with property values.*/
@Nullable
default Object postProcessBeforeInitialization(Object bean, String beanName) throws BeansException {
return bean;
} /**
* Apply this BeanPostProcessor to the given new bean instance <i>after</i> any bean
* initialization callbacks (like InitializingBean's {@code afterPropertiesSet}
* or a custom init-method). The bean will already be populated with property values.*/
@Nullable
default Object postProcessAfterInitialization(Object bean, String beanName) throws BeansException {
return bean;
}
从源码注释中可以看出,postProcessBeforeInitialization方法会在bean实例化和属性设置之后,自定义初始化方法(参考https://www.cnblogs.com/dubhlinn/p/10664402.html提到的3种方式)之前被调用,而postProcessAfterInitialization方法会在自定义初始化方法之后被调用。当容器中存在多个BeanPostProcessor的实现类时,会按照它们在容器中注册的顺序执行。对于自定义BeanPostProcessor实现类,还可以让其实现Ordered接口自定义排序。
后置处理器的注册方式
在ApplicationContext容器中,只需要按普通的bean注册即可;
但是在BeanFactory容器中,需要显示的调用addBeanPostProcessor()方法才能注册。
import org.springframework.beans.factory.config.BeanPostProcessor;
import org.springframework.core.Ordered; /**
* 自定义后置处理器
* 用于在bean的初始化前后进行扩展
* 这里的初始化,指的是初始化阶段调用的方法,
* 例如@Bean注解的initMethod、spring提供的InitializingBean接口、jsr-250提供的@PostConstruct接口
* 当容器中存在多个后置处理器时,默认会按照其在容器中注册的顺序执行
* 对于自定义后置处理器,也可以通过实现Ordered接口来自定义其执行顺序,数字越大优先级越低
*/
public class AppleBeanPostProcessor implements BeanPostProcessor, Ordered { /**
* 在初始化前执行的扩展逻辑
* @param bean
* @param beanName
* @return
* @throws BeansException
*/
@Override
public Object postProcessBeforeInitialization(Object bean, String beanName) throws BeansException {
if ("apple".equals(beanName)) {
System.out.println("创建了苹果对象...");
}
return bean;
} /**
* 在初始化后执行的扩展逻辑
* @param bean
* @param beanName
* @return
* @throws BeansException
*/
@Override
public Object postProcessAfterInitialization(Object bean, String beanName) throws BeansException {
if ("apple".equals(beanName)) {
System.out.println("苹果对象初始化完成...");
}
return bean;
} @Override
public int getOrder() {
return 3;
}
}
/**
* 用注册普通bean的方式注册自定义后置处理器
*/
@Configuration
@Import(value = {AppleBeanPostProcessor.class})
public class LifeBeanConfig2 {
}
后置处理器的作用
简单的说,后置处理器用于bean对象初始化前后进行逻辑增强。spring提供了BeanPostProcessor的很多实现类,例如AutowiredAnnotationBeanPostProcessor用于@Autowired注解的实现,AnnotationAwareAspectJAutoProxyCreator用于SpringAOP的动态代理等等。除此之外,我们还可以自定义BeanPostProcessor的实现类,在其中写入需要的逻辑。下面以AnnotationAwareAspectJAutoProxyCreator为例,说明后置处理器是怎样工作的。我们都知道springAOP的实现原理是动态代理,最终放入容器的是代理类的对象,而不是bean本身的对象,那么spring是什么时候做到这一步的?就是在AnnotationAwareAspectJAutoProxyCreator后置处理器的postProcessAfterInitialization方法,即bean对象初始化完成之后,后置处理器会判断该bean是否注册了切面,如果是,则生成代理对象注入容器
/**
* Create a proxy with the configured interceptors if the bean is
* identified as one to proxy by the subclass.
* @see #getAdvicesAndAdvisorsForBean
*/
@Override
public Object postProcessAfterInitialization(@Nullable Object bean, String beanName) {
if (bean != null) {
Object cacheKey = getCacheKey(bean.getClass(), beanName);
if (this.earlyProxyReferences.remove(cacheKey) != bean) {
return wrapIfNecessary(bean, beanName, cacheKey);
}
}
return bean;
}
spring的生命周期
所谓spring的生命周期,是指一个bean对象在容器中从创建到销毁的过程,大致会经历如下过程:
1. 执行bean的构造方法,生成bean对象
2. 执行bean的set方法,注入属性
3. 如果容器中存在BeanPostProcessor的实现类,则执行它们的postProcessorBeforeInitialization方法
4. 如果bean实现了InitializingBean接口,则执行afterPropertiesSet方法
5. 如果<bean>标签或@Bean注解中定义了init-method/initMethod,则执行其引用的方法
6. 如果容器中存在BeanPostProcessor的实现类,则执行它们的postProcessorAfterInitialization方法
7. 关闭容器时,如果bean实现了DisposableBean接口,则执行destroy方法
8. 关闭容器时,如果<bean>标签或@Bean注解中定义了destroy-method/destroyMethod,则执行其引用的方法
spring的后置处理器——BeanPostProcessor以及spring的生命周期的更多相关文章
- Spring的后置处理器BeanPostProcessor
一.BeanPostProcessor接口的作用 如果我们需要在Spring容器完成Bean的实例化.配置和其他的初始化前后添加一些自己的逻辑处理,我们就可以定义一个或者多个BeanPostProce ...
- Spring点滴五:Spring中的后置处理器BeanPostProcessor讲解
BeanPostProcessor接口作用: 如果我们想在Spring容器中完成bean实例化.配置以及其他初始化方法前后要添加一些自己逻辑处理.我们需要定义一个或多个BeanPostProcesso ...
- spring学习四:Spring中的后置处理器BeanPostProcessor
BeanPostProcessor接口作用: 如果我们想在Spring容器中完成bean实例化.配置以及其他初始化方法前后要添加一些自己逻辑处理.我们需要定义一个或多个BeanPostProcesso ...
- spring利用后置处理器初始化bean属性
spring利用后置处理器初始化bean属性 参考:http://blog.csdn.net/heyutao007/article/details/50326793 @Configurable @En ...
- spring后置处理器BeanPostProcessor
BeanPostProcessor的作用是在调用初始化方法的前后添加一些逻辑,这里初始化方法是指在配置文件中配置init-method,或者实现了InitializingBean接口的afterPro ...
- Spring Bean后置处理器
本例子源于:W3CSchool,在此作记录 Bean 后置处理器允许在调用初始化方法前后对 Bean 进行额外的处理. BeanPostProcessor 接口定义回调方法,你可以实现该方法来提供自己 ...
- 曹工杂谈:为什么很少需要改Spring源码,因为扩展点太多了,说说Spring的后置处理器
前言 最近发了好几篇,都是覆盖框架源码,但是spring的代码,我是从没覆盖过,毕竟,如果方便扩展,没谁想去改源码,而spring就是不需要改源码的那个,真的是"对扩展开放,对修改关闭&qu ...
- Spring Bean 后置处理器
Bean 后置处理器允许在调用初始化方法前后对 Bean 进行额外的处理. BeanPostProcessor 接口定义回调方法,你可以实现该方法来提供自己的实例化逻辑,依赖解析逻辑等. 你也可以在 ...
- Bean后置处理器 BeanPostProcessor
1.BeanPostProcessor接口的作用 Bean后置处理器允许在调用初始化方法前后对Bean进行额外的处理,Bean后置处理器对IOC容器的所有bean实例逐一处理,而非单一实例. 我们可以 ...
随机推荐
- IDEA 增加对JPA的支持 执行JPQL语句
IDEA 可以在控制台console中执行JPQL语句: 1. 在已存在的项目中选择项目结构: 2. 选择模块-指定实体所在的模块-选择上面的号 2. 选择要添加的模块:我们使用的是JPA,也可能有的 ...
- MAC设置环境变量
1. Mac 启动加载文件位置(可设置环境变量) ------------------------------------------------------- (1)首先要知道你使用的Mac OS ...
- 浏览器常用12种兼容问题(JS)
//1.滚动条到顶端的距离(滚动高度) var scrollTop = document.documentElement.scrollTop || document.body.scrollTop; / ...
- CSS行内框(内联元素)
行内框在一行中水平布置.可以使用水平内边距.边框和外边距调整它们的间距.但是,垂直内边距.边框和外边距不影响行内框的高度.由一行形成的水平框称为行框(Line Box),行框的高度总是足以容纳它包含的 ...
- switch语句小练习
java有两钟选择判断语句,分别是if else和switch case语句. 下面我们做一个switch case语句的练习. // 定义一个扫描器 Scanner sacnner = new Sc ...
- Qt是什么?Qt简介(非常全面)
http://c.biancheng.net/view/1792.html Qt(官方发音 [kju:t],音同 cute)是一个跨平台的 C++ 开发库,主要用来开发图形用户界面(Graphical ...
- (最新)2019年ICPC东亚地区-区域赛赛站网络赛以及现场赛时间安排
- pandas数据排序(series排序 & DataFrame排序)
# pandas数据排序 # series的排序: # Series.sort_values(ascending = True,inplace = False) # 参数说明: # ascending ...
- Git之旅(1):安装git
一.在windows中安装git git官网:https://git-scm.com/downloads 二.在centos系统安装git 2.1 配置base源和epel源 # cat /etc/y ...
- Maven项目的一些依赖
Maven构建的Spring项目需要哪些依赖? <!-- Spring依赖 --> <!-- 1.Spring核心依赖 --> <dependency> <g ...