spring 控制bean的两种扩展方式
1. 改变bean的定义(BeanFactoryPostProcessor接口).需实现 BeanFactoryPostProcessor.对其中的postProcessBeanFactory方法进行重写 通过ConfigurableListableBeanFactory 获取到类 ,再对类中的属性进行扩展.
@Component
public class CustomizeBeanFactoryPostProcessor implements BeanFactoryPostProcessor {
@Override
public void postProcessBeanFactory(ConfigurableListableBeanFactory beanFactory) throws BeansException {
AbstractBeanDefinition abstractBeanDefinition = (AbstractBeanDefinition) beanFactory.getBeanDefinition("calculateService");
MutablePropertyValues pv = abstractBeanDefinition.getPropertyValues();
pv.addPropertyValue("desc", "Desc is changed from bean factory post processor");
abstractBeanDefinition.setScope(BeanDefinition.SCOPE_SINGLETON);
}
}
2. 只改变实例化对象(BeanFactoryProcessor接口)
@Component
public class CustomizeBeanFactoryPostProcessor implements BeanPostProcessor {
@Override
public Object postProcessBeforeInitialization(Object bean, String beanName) throws BeansException {
if ("calculateService".equals(beanName)) {
//打印当前堆栈
Utils.printTrack("do postProcess before initialization");
CalculateService calculateService = (CalculateService) bean;
//修改calculateService实例的成员变量serviceDesc的值
calculateService.setServiceDesc("desc from " + this.getClass().getSimpleName());
}
return bean;
}
@Override
public Object postProcessAfterInitialization(Object bean, String beanName) throws BeansException {
if ("calculateService".equals(beanName)) {
//打印当前堆栈
Utils.printTrack("do postProcess after initialization");
}
return bean;
}
}
spring 执行BeanPostProcessor:
1. 初始化时,spring容器会有特殊处理,会直接调用beanFactory.addBeanPostProcessor进行注册(例如AbstractApplicationContext类的PrepareBeanFactory方法中就有);
2. 找出所有实现了BeanPostProcessor皆苦中bean,注册到容器,注册顺序如下:
第一:实现了PriorityOrdered接口的,排序后;
第二; 实现leOrdered接口的排序后;
第三:既没实现PriorityOrdered接口,也没有实现Ordered接口的;
第四:实现了Merged Bean DefinitionPorstProcessor接口的(这些耶按照PriorityOrdered,Ordered等逻辑);
第五:实例化一个ApplicationListenerDetector对象
3.实例化bean的时候,对于每个bean,先用mergedbeanDefinitionPostProcessor实现类的postProcessMergedbeandefinition方法处理每个bean的定义类;
4. 再用BeanPostProcessor的postProcessBeforeInitialization方法处理每个bean实例;\
5 bean实例化初始化
5.用BeanPostProcessor的postProcessAfterInitialization方法处理每个bean实例;