文章目录
InstantiationAwareBeanPostProcessor
- InstantiationAwareBeanPostProcessor是BeanPostProcessor接口的一个子接口,除了继承了BeanPostProcessor的
2个环绕处理方法之外,自己还定义了3个方法,继承自BeanPostProcessor的方法是作用于Bean初始化前后,自己定义的2个方法
作用于Bean的实例化前后,注意实例化在初始化之前,另外还有一个方法用于赋值,详情如下:
public interface InstantiationAwareBeanPostProcessor extends BeanPostProcessor {
/**
* 1.实例化之前执行
*/
@Nullable
default Object postProcessBeforeInstantiation(Class<?> beanClass, String beanName) throws BeansException {
return null;
}
/**
* 2.实例化之后执行
*/
default boolean postProcessAfterInstantiation(Object bean, String beanName) throws BeansException {
return true;
}
/**
* 3.赋值操作,比如依赖注入时,@Autowire和@Value注解的值的注入就是基于该方法
*/
@Nullable
default PropertyValues postProcessPropertyValues( PropertyValues pvs, PropertyDescriptor[] pds, Object bean, String beanName) throws BeansException {
return pvs;
}
}
public interface BeanPostProcessor {
/**
* 1.初始化之前执行
*/
@Nullable
default Object postProcessBeforeInitialization(Object bean, String beanName) throws BeansException {
return bean;
}
/**
* 2.初始化之后执行
*/
@Nullable
default Object postProcessAfterInitialization(Object bean, String beanName) throws BeansException {
return bean;
}
}
- 这里我们可以知道InstantiationAwareBeanPostProcessor和他的父接口BeanPostProcessor各代表了一种扩展点,前者是实例化前后
调用,后置是初始化前后调用,这对应着不同的bean的生命周期阶段。
一、调用时机
-
我们首先还是看看InstantiationAwareBeanPostProcessor接口自己定义的三个方法的调用时机,我们通过bean的生命周期源码的方法跟进,
跟进到AbstractAutowireCapableBeanFactory#createBean()#line 462
(可以参考03-spring BeanPostProcessor文章中的BeanPostProcessor方法的调用时机小节) -
AbstractAutowireCapableBeanFactory#createBean()#line 462。这里我们看到注释,意思是给BeanPostProcessors一个机会返回一个目
标bean的代理,如果返回了的话,那么就直接return了
@Override
protected Object createBean(String beanName, RootBeanDefinition mbd, @Nullable Object[] args)
throws BeanCreationException {
//---省略----
try {
// Give BeanPostProcessors a chance to return a proxy instead of the target bean instance.
//1.给BeanPostProcessors一个机会返回一个目标bean的代理
Object bean = resolveBeforeInstantiation(beanName, mbdToUse);
//2.如果给一个机会,BeanPostProcessors把握了机会成功返回了一个bean,那么就直接return
if (bean != null) {
return bean;
}
}
//---省略----
//3.如果给一个机会,BeanPostProcessors没有把握不能返回了一个bean,那么就走创建流程
Object beanInstance = doCreateBean(beanName, mbdToUse, args);
//---省略----
}
- AbstractAutowireCapableBeanFactory#resolveBeforeInstantiation()#line 1033。前面给的一个机会就在这个方法里面执行,这里很有意思,但是第
一次看会很糊涂,而且本文我写的也不是非常详细,具体在最后给出一个分析bean创建总体流程的文章才能说明白。这里的意思是先执行InstantiationAwareBeanPostProcessor
接口的postProcessBeforeInstantiation方法,来看能不能返回一个bean(从前面的注释看出这里是尝试获取一个目标bean的代理),如果获取到了,就直接
执行BeanPostProcessor#postProcessAfterInitialization方法,注意执行的是它的父类的后置方法,而不是自己的后置方法,也就是这里实际上跳过了
BeanPostProcessor的前置方法和InstantiationAwareBeanPostProcessor自身的后置方法以及赋值方法,我们之前理解的bean的生
命周期里面一般是下面这样的(只包含部分核心流程):
InstantiationAwareBeanPostProcessor前置方法执行->InstantiationAwareBeanPostProcessor后置方法执行->InstantiationAwareBeanPostProcessor赋值方法执行->BeanPostProcessor前置方法执行->初始化->BeanPostProcessor后置方法执行
在这里流程是下面这样的。也就是说这样的流程,BeanPostProcessor的前置方法根本没有执行,并且跳过了InstantiationAwareBeanPostProcessor自身的赋值方法和后置方法。
InstantiationAwareBeanPostProcessor前置方法执行返回bean成功->BeanPostProcessor后置方法执行->bean创建成功
- 这里第一次看估计绕进去出不来,后续参考08-spring Bean生命周期详细图解
@Nullable
protected Object resolveBeforeInstantiation(String beanName, RootBeanDefinition mbd) {
Object bean = null;
//一个布尔变量记录是否被处理过
if (!Boolean.FALSE.equals(mbd.beforeInstantiationResolved)) {
// Make sure bean class is actually resolved at this point.
if (!mbd.isSynthetic() && hasInstantiationAwareBeanPostProcessors()) {
Class<?> targetType = determineTargetType(beanName, mbd);
if (targetType != null) {
//1.先调用InstantiationAwareBeanPostProcessor的前置方法,尝试获取一个bean(实际上是目标bean的一个代理)
bean = applyBeanPostProcessorsBeforeInstantiation(targetType, beanName);
if (bean != null) {
//2.获取一个bean成功,那么直接执行BeanPostProcessor的后置处理方法,相当于将InstantiationAwareBeanPostProcessor的
//后置处理方法,赋值方法,以及BeanPostProcessor的前置处理方法都跳过了,会直接返回bean,代表创建bean结束
bean = applyBeanPostProcessorsAfterInitialization(bean, beanName);
}
}
}
mbd.beforeInstantiationResolved = (bean != null);
}
return bean;
}
//InstantiationAwareBeanPostProcessor前置方法执行
protected Object applyBeanPostProcessorsBeforeInstantiation(Class<?> beanClass, String beanName) {
for (BeanPostProcessor bp : getBeanPostProcessors()) {
if (bp instanceof InstantiationAwareBeanPostProcessor) {
InstantiationAwareBeanPostProcessor ibp = (InstantiationAwareBeanPostProcessor) bp;
Object result = ibp.postProcessBeforeInstantiation(beanClass, beanName);
if (result != null) {
return result;
}
}
}
return null;
}
//BeanPostProcessor后置方法执行
public Object applyBeanPostProcessorsAfterInitialization(Object existingBean, String beanName)
throws BeansException {
Object result = existingBean;
for (BeanPostProcessor beanProcessor : getBeanPostProcessors()) {
Object current = beanProcessor.postProcessAfterInitialization(result, beanName);
if (current == null) {
return result;
}
result = current;
}
return result;
}
二、实现类
2.1 AutowiredAnnotationBeanPostProcessor
- 在前面我们分析过,AutowiredAnnotationBeanPostProcessor是InstantiationAwareBeanPostProcessor接口的主要实现类,其支持的功能也是我们使用最多的。前面
有一篇文章来介绍AutowiredAnnotationBeanPostProcessor,详情参考04-spring AutowiredAnnotationBeanPostProcessor
2.2 AspectJAwareAdvisorAutoProxyCreator
- AspectJAwareAdvisorAutoProxyCreator是AOP的核心类,我们在前面的注释里说到,在InstantiationAwareBeanPostProcessor的postProcessBeforeInstantiation方法里面尝试返回一个
目标bean的动态代理,而AOP底层就是动态代理,这里就是AOP的切入点。思路是在这里通过AOP的核心类返回了一个bean的动态代理对象而不是真正的去创建目标bean,这里我们不对
AspectJAwareAdvisorAutoProxyCreator做深入的分析,放到后面AOP的专门文章中分析。
三、小结
- 本文我们主要分析了InstantiationAwareBeanPostProcessor接口的结构,然后从bean的整个生命周期分析接口方法的调用时机,并区别其自己的方法和继承自BeanPostProcessor接口的方法
之间的区别。最后我们回到之前分析过的AutowiredAnnotationBeanPostProcessor类,分析接口方法在这个类中所起的作用。 - InstantiationAwareBeanPostProcessor接口主要是在Spring框架中使用,通过分析我们可以更好的了解bean的生命周期和基于该接口实现的注解功能及其对应原理。