基于Spring AOP做事务控制,在引入BeanFactoryPostProcessor(BeanPostProcessor也一样)之前,一切OK。
但是在一个类实现了BeanFactoryPostProcessor接口,并通过以下代码进行处理时,发现很多原本由Spring代理的类,现在Spring不会代理了,而是直接实例化原始类。
代码如:
public void postProcessBeanFactory(ConfigurableListableBeanFactory beanFactory) throws BeansException{
Iterator ite = factory.getBeansOfType(MyProcessor.class).values().iterator();
while(ite.hasNext()) registerProcessor((MyProcessor) ite.next());
}
后来修改为实现ApplicationContextAware:
public void setApplicationContext(ApplicationContext applicationContext) throws BeansException {
Iterator ite = applicationContext.getBeansOfType(MyProcessor.class).values().iterator();
while(ite.hasNext()) registerProcessor((MyProcessor) ite.next());
}
就一切OK了。
为此写了一个从Spring环境中获取特定类型Bean的基类:
public abstract class BeanAware implements ApplicationContextAware{
protected ApplicationContext appContext = null;
final public void setApplicationContext(ApplicationContext applicationContext) throws BeansException {
……
Map beans = applicationContext.getBeansOfType(getClass());
setBeanInstance((BeanAware) beans.values().iterator().next());
this.appContext = applicationContext;
afterApplicationContextInit(applicationContext);
}
/**
* 实现本方法,接收spring组装的bean实例
* @param bean spring组装的bean实例
*/
protected abstract void setBeanInstance(BeanAware bean);
/**
* Spring的上下文环境初始化完毕后的通知
* @param appContext
*/
protected void afterApplicationContextInit(ApplicationContext appContext) {
}
}
基于AOP实现配置时,实现此基类,就可以正确的获得当前Bean实例和特定类型的Bean实例。
原因:BeanFactoryPostProcessor is designed to PostProcess a BeanFactory NOT the ApplicationContext. Bean in the Bean factory don't have transactions etc, only after the processing in the ApplicationContext the have transactions etc.