Spring Framework源码解析——BeanPostProcessor
版权声明
- 本文原创作者:谷哥的小弟
- 作者博客地址:http://blog.csdn.net/lfdfhl
一、概述
BeanFactoryPostProcessor
是 Spring IoC 容器中用于在容器实例化任何 Bean 之前,对 BeanFactory
本身进行定制化修改的核心扩展接口。它允许开发者在 Spring 容器启动过程中,修改已注册的 BeanDefinition
元数据,例如更改属性值、添加依赖、注册新的 Bean、修改作用域等。
与 BeanPostProcessor
(作用于 Bean 实例)不同,BeanFactoryPostProcessor
作用于 BeanDefinition 阶段,是 Spring 容器可扩展性的重要体现之一。
二、接口定义
public interface BeanFactoryPostProcessor {/*** 在所有 BeanDefinition 加载完成后,但在任何 Bean 被实例化前调用* @param beanFactory 当前使用的 BeanFactory(通常是 ConfigurableListableBeanFactory)* @throws BeansException 如果处理失败*/void postProcessBeanFactory(ConfigurableListableBeanFactory beanFactory) throws BeansException;
}
核心特征如下:
- 执行时机早:在
refresh()
流程中,早于 Bean 实例化; - 操作对象是
BeanFactory
和BeanDefinition
,而非 Bean 实例; - 可以修改、注册、删除
BeanDefinition
; - 通常用于配置处理、占位符替换、条件注册等场景。
三、注册与执行机制
注册方式如下:
BeanFactoryPostProcessor
可通过以下方式注册:
- 作为普通 Bean 被 Spring 扫描并注册(如使用
@Component
); - 通过
ApplicationContext.addBeanFactoryPostProcessor()
手动添加; - Spring 内部自动注册(如
ConfigurationClassPostProcessor
、PropertySourcesPlaceholderConfigurer
)。
注意:
BeanFactoryPostProcessor
必须是单例,否则不会被识别。
四、核心执行流程:invokeBeanFactoryPostProcessors
该方法是 BeanFactoryPostProcessor
执行的核心逻辑,定义在 AbstractApplicationContext
中。
protected void invokeBeanFactoryPostProcessors(ConfigurableListableBeanFactory beanFactory) {PostProcessorRegistrationDelegate.invokeBeanFactoryPostProcessors(beanFactory, getBeanFactoryPostProcessors());
}
实际执行委托给 PostProcessorRegistrationDelegate
类
public static void invokeBeanFactoryPostProcessors(ConfigurableListableBeanFactory beanFactory, List<BeanFactoryPostProcessor> beanFactoryPostProcessors) {Set<String> processedBeans = new HashSet<>();// 1. 处理实现了 PriorityOrdered 接口的 BeanFactoryPostProcessorList<BeanFactoryPostProcessor> priorityOrderedPostProcessors = new ArrayList<>();for (BeanFactoryPostProcessor postProcessor : beanFactoryPostProcessors) {if (postProcessor instanceof PriorityOrdered) {priorityOrderedPostProcessors.add(postProcessor);}}sortPostProcessors(priorityOrderedPostProcessors, beanFactory);invokeBeanFactoryPostProcessors(priorityOrderedPostProcessors, beanFactory);// 2. 处理实现了 Ordered 接口的 BeanFactoryPostProcessorList<BeanFactoryPostProcessor> orderedPostProcessors = new ArrayList<>();for (BeanFactoryPostProcessor postProcessor : beanFactoryPostProcessors) {if (!processedBeans.contains(postProcessor) && postProcessor instanceof Ordered) {orderedPostProcessors.add(postProcessor);}}sortPostProcessors(orderedPostProcessors, beanFactory);invokeBeanFactoryPostProcessors(orderedPostProcessors, beanFactory);// 3. 处理其余的 BeanFactoryPostProcessor(无排序)List<BeanFactoryPostProcessor> nonOrderedPostProcessors = new ArrayList<>();for (BeanFactoryPostProcessor postProcessor : beanFactoryPostProcessors) {if (!processedBeans.contains(postProcessor) && !(postProcessor instanceof PriorityOrdered || postProcessor instanceof Ordered)) {nonOrderedPostProcessors.add(postProcessor);}}invokeBeanFactoryPostProcessors(nonOrderedPostProcessors, beanFactory);// 4. 从 BeanFactory 中获取 BeanFactoryPostProcessor 类型的 Bean 并执行String[] postProcessorNames = beanFactory.getBeanNamesForType(BeanFactoryPostProcessor.class, true, false);List<BeanFactoryPostProcessor> registryProcessors = new ArrayList<>();List<BeanFactoryPostProcessor> regularPostProcessors = new ArrayList<>();for (String ppName : postProcessorNames) {if (!processedBeans.contains(ppName)) {BeanFactoryPostProcessor pp = beanFactory.getBean(ppName, BeanFactoryPostProcessor.class);if (pp instanceof BeanDefinitionRegistryPostProcessor) {registryProcessors.add(pp);} else {regularPostProcessors.add(pp);}}}// 4.1 先执行 BeanDefinitionRegistryPostProcessor(特殊子接口)invokeBeanDefinitionRegistryPostProcessors(registryProcessors, registry);// 4.2 再执行普通的 BeanFactoryPostProcessorinvokeBeanFactoryPostProcessors(regularPostProcessors, beanFactory);
}
五、BeanDefinitionRegistryPostProcessor
:更早的扩展点
BeanDefinitionRegistryPostProcessor
是 BeanFactoryPostProcessor
的子接口,提供了更早的介入时机。
public interface BeanDefinitionRegistryPostProcessor extends BeanFactoryPostProcessor {/*** 在标准的 postProcessBeanFactory 之前调用* 允许注册新的 BeanDefinition*/void postProcessBeanDefinitionRegistry(BeanDefinitionRegistry registry) throws BeansException;
}
执行顺序如下:
postProcessBeanDefinitionRegistry()
:允许注册新的 BeanDefinition;postProcessBeanFactory()
:允许修改已存在的 BeanDefinition。
典型应用:
ConfigurationClassPostProcessor
就是BeanDefinitionRegistryPostProcessor
的实现,负责解析@Configuration
类,扫描@Component
,处理@Import
等。
六、核心方法详解
invokeBeanFactoryPostProcessors(List<...>, BeanFactory)
如下:
private static void invokeBeanFactoryPostProcessors(Collection<? extends BeanFactoryPostProcessor> postProcessors, ConfigurableListableBeanFactory beanFactory) {for (BeanFactoryPostProcessor postProcessor : postProcessors) {postProcessor.postProcessBeanFactory(beanFactory);}
}
- 遍历所有
BeanFactoryPostProcessor
; - 按顺序调用
postProcessBeanFactory
方法; - 每个处理器都可以修改
beanFactory
中的BeanDefinition
。
七、Spring 内置常用 BeanFactoryPostProcessor
实现
类名 | 功能 |
---|---|
ConfigurationClassPostProcessor | 解析 @Configuration 、@ComponentScan 、@Import 、@Bean 等注解,注册 BeanDefinition |
PropertySourcesPlaceholderConfigurer | 替换 ${...} 占位符(如数据库配置) |
CustomAutowireConfigurer | 配置自定义的自动装配策略 |
LoadTimeWeaverConfigurer | 配置加载时织入(LTW) |
MapperScannerConfigurer (MyBatis-Spring) | 扫描 MyBatis Mapper 接口并注册为 Bean |
八、自定义 BeanFactoryPostProcessor
示例
8.1 修改 Bean 属性
@Component
public class CustomBeanFactoryPostProcessor implements BeanFactoryPostProcessor {@Overridepublic void postProcessBeanFactory(ConfigurableListableBeanFactory beanFactory) throws BeansException {// 获取某个 Bean 的定义BeanDefinition bd = beanFactory.getBeanDefinition("myService");// 修改其属性MutablePropertyValues pv = bd.getPropertyValues();pv.add("timeout", 5000); // 设置超时时间// 修改作用域bd.setScope(BeanDefinition.SCOPE_PROTOTYPE);}
}
8.2 动态注册新 Bean
@Component
public class DynamicBeanRegistrationPostProcessor implements BeanDefinitionRegistryPostProcessor {@Overridepublic void postProcessBeanDefinitionRegistry(BeanDefinitionRegistry registry) throws BeansException {// 动态注册一个新 BeanBeanDefinitionBuilder builder = BeanDefinitionBuilder.genericBeanDefinition(MyDynamicBean.class);builder.addPropertyValue("name", "dynamicBean");registry.registerBeanDefinition("dynamicBean", builder.getBeanDefinition());}@Overridepublic void postProcessBeanFactory(ConfigurableListableBeanFactory beanFactory) throws BeansException {// 可选:进一步修改 BeanFactory}
}
九、与 BeanPostProcessor
的对比
对比项 | BeanFactoryPostProcessor | BeanPostProcessor |
---|---|---|
作用对象 | BeanFactory / BeanDefinition | Bean 实例 |
执行时机 | 所有 BeanDefinition 加载后,Bean 实例化前 | Bean 实例化后,初始化前后 |
主要用途 | 修改 Bean 元数据、注册新 Bean、配置替换 | 增强 Bean 行为、创建代理、属性注入 |
典型应用 | @Configuration 解析、${} 替换 | @Autowired 、AOP 代理 |
执行顺序 | 更早 | 较晚 |
十、执行顺序控制
BeanFactoryPostProcessor
的执行顺序遵循以下优先级:
PriorityOrdered
实现:最高优先级;Ordered
实现:次高优先级;- 无排序接口的处理器:最后执行;
- 通过
ApplicationContext.addBeanFactoryPostProcessor()
添加的处理器优先于容器中注册的 Bean。
可通过实现
Ordered
接口或使用@Order
注解控制顺序。
BeanFactoryPostProcessor
是 Spring 容器生命周期中最早可扩展的切入点之一,它允许开发者在 Bean 实例化之前对容器的元数据进行修改。理解其源码执行流程与设计思想,有助于深入掌握 Spring 的配置驱动、自动装配、条件注册等高级特性。
BeanFactoryPostProcessor核心要点小结:
BeanFactoryPostProcessor
作用于BeanDefinition
阶段;- 执行时机早于 Bean 实例化;
- 支持修改、注册、删除
BeanDefinition
; BeanDefinitionRegistryPostProcessor
提供更早的注册能力;- Spring 内部多个核心功能(如
@Configuration
、@ComponentScan
)依赖此机制; - 自定义实现可用于动态配置、条件注册、属性增强等场景。