spring的后置处理器有两类,bean后置处理器,bf(BeanFactory)后置处理器。bean后置处理器作用于bean的生命周期,bf的后置处理器作用于bean工厂的生命周期。
BF后置处理器
Spring是一个bean依赖注入容器,容器是BF,它的上级对象是applicationContxt,applicationContxt在容器功能上附加了一下新的功能。我们使用spring时,用的都是applicationConext的实现类。
我们在初始化这些applicationConext时,最终调用的都是org.springframework.context.support.AbstractApplicationContext#refresh方法用于容器的初始化。这个方法是一个模板方法,规定了容器实例化的步骤。其中BF初始化完成后,会调用BF的后置处理器对BF进行后置处理。而后置处理器的调用是在org.springframework.context.support.AbstractApplicationContext#invokeBeanFactoryPostProcessors这个方法中进行的。
BF的后置处理器有两种,BeanFactoryPostProcessor和BeanDefinitionRegistryPostProcessor。BF后置处理器和BD(BeanDefinition)后置处理器。BD后置处理器是BF后置处理器的子接口。下面是BF后置处理器的api截图。
invokeBeanFactoryPostProcessors方法内,调用后置处理器的步骤如下:
- 通过ac(applicationContext)的addBeanFactoryPostProcessor方法加入的BD后置处理器,按照加入顺序调用。
- ac中类型为bd后置处理器的,拥有PriorityOrdered接口的BD后置处理器。
- ac中类型为bd后置处理器的,拥有Ordered接口的BD后置处理器。
- ac中类型为bd后置处理器的,PriorityOrdered和Ordered接口都没实现的BeanDefinitionRegistryPostProcessor
- ac中类型为bf后置处理器的,拥有PriorityOrdered接口的BF后置处理器。
- ac中类型为bf后置处理器的,拥有Ordered接口的BF后置处理器。
- ac中类型为bf后置处理器的,PriorityOrdered和Ordered接口都没实现的BeanFactoryPostProcessor
在AnnotationConfigApplicationContext上下文中,会有一个关键的BD后置处理器:ConfigurationClassPostProcessor。它是用来扫描所有交给spring管理的注解类的。将其解析为BD实例放到AC中去。
Bean后置处理器
spring管理的是bean,所以bean的实例化是一个重要的过程。spring是通过org.springframework.beans.factory.support.AbstractBeanFactory#getBean方法实例化并初始化Bean。实例化Bean的过程中,可以通过bean的后置处理器插手Bean的实例化过程。
Bean的实例化过程如下:
- 解析BD
- 确定构造方法
- 用构造方法实例化(构造方法依赖不能进行循环依赖)
- 属性注入
- 初始化
在这个过程中,spring内设了8个bean的后置处理器调用点,用来进行扩展。
Bean后置处理器有五种:
- BeanPostProcessor:基本后置处理器,有两个方法,分别在Bean初始化前后调用
- postProcessBeforeInitialization在初始化之前调用
- postProcessAfterInitialization在初始化之后调用
- DestructionAwareBeanPostProcessor在bean被摧毁的时候调用
- InstantiationAwareBeanPostProcessor:有三个方法,
- postProcessBeforeInstantiation在最开始调用,如果返回Bean实例不为空,直接调用BeanPostProcessor的postProcessAfterInitialization方法,返回该bean,不在进行其他动作。
- postProcessAfterInstantiation判断是否需要进行属性填充
- postProcessPropertyValues,进行属性填充前,处理bean的PropertyValues。用于属性填充
- MergedBeanDefinitionPostProcessor,只有一个方法,postProcessMergedBeanDefinition,在实例化之前,对BD进行后置处理。
- SmartInstantiationAwareBeanPostProcessor,有三个方法
- predictBeanType,预测InstantiationAwareBeanPostProcessor#postProcessBeforeInstantiation方法返回的类型。
- determineCandidateConstructors,确定该bd的构造函数,找不到用默认的构造函数
- getEarlyBeanReference,在需要获取earlyBean时,在返回earlyBean前对earlyBean进行后置处理。
Bean后置处理器的API截图: