简介
BeanFactoryPostProcessors: 通过实现该接口,重写postProcessBeanFactory(ConfigurableListableBeanFactory beanFactory)
方法,可以在bean未实例化之前通过beanFactory得到bean定义,并可以修改属性值。
* 扩展原理:
* BeanPostProcessor:bean后置处理器,bean创建对象初始化前后进行拦截工作的
*
* 1、BeanFactoryPostProcessor:beanFactory的后置处理器;
* 在BeanFactory标准初始化之后调用,来定制和修改BeanFactory的内容;
* 所有的bean定义已经保存加载到beanFactory,但是bean的实例还未创建
*
*
* BeanFactoryPostProcessor原理:
* 1)、ioc容器创建对象
* 2)、invokeBeanFactoryPostProcessors(beanFactory);
* 如何找到所有的BeanFactoryPostProcessor并执行他们的方法;
* 1)、直接在BeanFactory中找到所有类型是BeanFactoryPostProcessor的组件,并执行他们的方法
* 2)、在初始化创建其他组件前面执行
案例
创建一个自定义 BeanFactoryPostProcessor 。
import org.springframework.beans.BeansException;
import org.springframework.beans.factory.config.BeanFactoryPostProcessor;
import org.springframework.beans.factory.config.ConfigurableListableBeanFactory;
import org.springframework.stereotype.Component;
import java.util.Arrays;
@Component
public class MyBeanFactoryPostProcessor implements BeanFactoryPostProcessor {
@Override
public void postProcessBeanFactory(ConfigurableListableBeanFactory beanFactory) throws BeansException {
System.out.println("MyBeanFactoryPostProcessor...postProcessBeanFactory...");
int count = beanFactory.getBeanDefinitionCount();
String[] names = beanFactory.getBeanDefinitionNames();
System.out.println("当前BeanFactory中有"+count+" 个Bean");
System.out.println(Arrays.asList(names));
}
}
配置类
@Configuration
@ComponentScan("com.demo")
public class SpringConfig {
@Bean
public Blue blue(){
return new Blue();
}
}
测试类
@Test
public void test(){
AnnotationConfigApplicationContext applicationContext = new AnnotationConfigApplicationContext(SpringConfig.class);
applicationContext.close();
}
输出结果
MyBeanFactoryPostProcessor...postProcessBeanFactory...
当前BeanFactory中有9 个Bean
[org.springframework.context.annotation.internalConfigurationAnnotationProcessor, org.springframework.context.annotation.internalAutowiredAnnotationProcessor, org.springframework.context.annotation.internalRequiredAnnotationProcessor, org.springframework.context.annotation.internalCommonAnnotationProcessor, org.springframework.context.event.internalEventListenerProcessor, org.springframework.context.event.internalEventListenerFactory, springConfig, myBeanFactoryPostProcessor, blue]
blue...constructor
可以发现在创建对象之前就已经执行了自定义BeanFactoryPostProcessor 中的方法了。
用Debug跟踪源码,一直跟踪到循环执行IOC容器中的所有BeanFactoryPostProcessor代码如下。
BeanFactoryPostProcessor 修改 BeanDefinition 定义
@Component
public class MyBeanFactoryPostProcessor implements BeanFactoryPostProcessor {
@Override
public void postProcessBeanFactory(ConfigurableListableBeanFactory beanFactory) throws BeansException {
GenericBeanDefinition beanDefinition = (GenericBeanDefinition) beanFactory.getBeanDefinition("a");
//beanDefinition.setLazyInit(true);
//beanDefinition.setBeanClass(B.class);
GenericBeanDefinition beanDefinitionB = (GenericBeanDefinition) beanFactory.getBeanDefinition("b");
ConstructorArgumentValues constructorArgumentValues = new ConstructorArgumentValues();
constructorArgumentValues.addIndexedArgumentValue(0, "James");
beanDefinitionB.setConstructorArgumentValues(constructorArgumentValues);
}
}
面试
BeanFactoryPostProcessor 是容器的扩展点,它用于 IOC 容器的生命周期中,所有 BeanDefinition 都注册到 BeanFactory 后回调触发,用于访问 / 修改已经存在的 BeanDefinition 。与 BeanPostProcessor 相同,它们都是容器隔离的,不同容器中的 BeanFactoryPostProcessor 不会相互起作用。
关键回答点: 改变 Bean 的定义信息