2

我需要使用自定义 AnnotationTransactionAttributeSource 来拦截事务属性。现在,我使用 TransactionInterceptor 执行此操作并将其注入 TransactionAttributeSourceAdvisor 。代理是使用 DefaultAdvisorAutoProxyCreator 创建的,如下所示。

<bean class="org.springframework.aop.framework.autoproxy.DefaultAdvisorAutoProxyCreator"/>

<bean class="org.springframework.transaction.interceptor.TransactionAttributeSourceAdvisor">
    <property name="transactionInterceptor" ref="txInterceptor"/>
</bean>

<bean id="txInterceptor" class="org.springframework.transaction.interceptor.TransactionInterceptor">
    <property name="transactionManager" ref="txManager"/>
    <property name="transactionAttributeSource"> 
       <bean class="org.myProject.transaction.CustomAnnotationTransactionAttributeSource"/>
    </property>
</bean>

在这里,CustomAnnotationTransactionAttributeSource 扩展了 AnnotationTransactionAttributeSource。有什么办法可以强制 Tx:annotation-driven 使用我的 CustomAnnotationTransactionAttributeSource 以便我可以避免所有这些配置?. 我在其中一篇文章中读到,这可以通过使用 BeanPostProcessors 来完成,但不确定如何在这种情况下使用它。

4

1 回答 1

4

<tx:annotation-driven>它不会做任何神奇的事情,它只是注册几乎与手动操作相同的 bean 定义(请参阅 参考资料AnnotationDrivenBeanDefinitionParser)。

因此,您可以替换对AnnotationTransactionAttributeSource其他 bean 的引用,或者替换其定义中的类名属性。后者看起来更简单(尽管在 Spring 代码的更改方面更脆弱),可以通过以下方式完成BeanFactoryPostProcessor

public class AnnotationTransactionAttributeSourceReplacer implements BeanFactoryPostProcessor {
    public void postProcessBeanFactory(ConfigurableListableBeanFactory factory)
            throws BeansException {

        String[] names = factory.getBeanNamesForType(AnnotationTransactionAttributeSource.class);

        for (String name: names) {
            BeanDefinition bd = factory.getBeanDefinition(name);
            bd.setBeanClassName("org.myProject.transaction.CustomAnnotationTransactionAttributeSource");
        }            
    }       
}
于 2011-11-29T20:22:40.090 回答