春季使用了错误的交易管理器

时间:2019-04-08 06:27:36

标签: spring spring-transactions spring-kafka

我有两个春季交易经理。

  1. txManager1 -配置了数据源DB1的ChainedKafkaTransactionManager(KafkaTransactionManager,JpaTransactionManager)
  2. txManager2 -使用数据源DB2配置的JpaTransactionManager

问题是我使用txManager2执行某些操作,但是以某种方式使用txManager1而不是txManager2,并且数据已提交到DB1而不是DB2。

@Autowired
@Qualifier("common-tx")
private PlatformTransactionManager txManager2 ;

@KafkaListener(topics = "${kafka.topic.name}", groupId = "group-1", containerFactory = "customKafkaListenerContainerFactory")
public void topicListener(String message, Acknowledgment ack)
        throws InterruptedException, ClassNotFoundException, IOException {


    DefaultTransactionDefinition def = new DefaultTransactionDefinition();
    def.setName(domainEvent.getEventId());
    def.setPropagationBehavior(TransactionDefinition.PROPAGATION_REQUIRES_NEW);

    TransactionStatus commonStatus = txManager2 .getTransaction(def);

    someService.doSomething();

    txManager2 .commit(commonStatus);


    ack.acknowledge();
}

doSomething()中,我只是保留一个实体,调试后发现,通过Spring数据存储库保存该实体时,事务管理器  invokeWithinTransaction()的{​​{1}}中确定是错误的,即选择了txManager1而不是txManager2,这是配置问题还是我遗漏了什么?

txManager1配置:

org.springframework.transaction.interceptor.TransactionAspectSupport

txManager2配置:

    @Configuration
    @EnableTransactionManagement
    @PropertySource(value = {"classpath:application-${spring.profiles.active}.properties"})
    @Profile({"development","production","qa"})
    @EnableJpaRepositories(basePackages={"xxx.xxx.xxxx"},excludeFilters=@ComponentScan.Filter(type=FilterType.REGEX, pattern="xxx.xxx.xxxx.module2.*"))
    public class JPAConfig1 {

    @Value("${jndi.name}")
    private String jndiName;

    @Value("${hibernate.dialect}")
    private String hibernateDialect;

    @Value("${hibernate.show_sql}")
    private String showSql;

    @Value("${hibernate.format_sql}")
    private String formatSql;

    @Value("${hibernate.hbm2ddl.auto}")
    private String hiberanteUpdate;

    @Value("${javax.persistence.validation.mode}")
    private String hibernateValidation;



    @Bean
    @Primary
    public LocalContainerEntityManagerFactoryBean entityManagerFactory(MultiTenantConnectionProviderImpl tenantConnection, CurrentTenantIdentifierResolver currentTenantIdentifierResolver)
    {
        LocalContainerEntityManagerFactoryBean emf = new LocalContainerEntityManagerFactoryBean();
        JpaVendorAdapter vendorAdapter = new HibernateJpaVendorAdapter();
        emf.setJpaVendorAdapter(vendorAdapter);
        emf.setJpaProperties(jpaProperties(tenantConnection, currentTenantIdentifierResolver));
        emf.setPackagesToScan(new String[] {"xxx.xxx.xxxx"});

        return emf;
    }

    private Properties jpaProperties(MultiTenantConnectionProviderImpl tenantConnection, CurrentTenantIdentifierResolver currentTenantIdentifierResolver) {
        Properties properties = new Properties();
        properties.setProperty("hibernate.dialect",hibernateDialect);        
        properties.setProperty("hibernate.show_sql",showSql);
        properties.setProperty("hibernate.format_sql",formatSql);
        properties.setProperty("hibernate.hbm2ddl.auto",hiberanteUpdate);
        properties.setProperty("javax.persistence.validation.mode",hibernateValidation);

        properties.put(Environment.MULTI_TENANT, MultiTenancyStrategy.DATABASE);
        properties.put(Environment.MULTI_TENANT_IDENTIFIER_RESOLVER, currentTenantIdentifierResolver);
        properties.put(Environment.MULTI_TENANT_CONNECTION_PROVIDER, tenantConnection);

        return properties;
    }

    @Bean
    public CurrentTenantIdentifierResolver getCurrentTenantIdentifierResolver(TenantContext tenantContext) {
        return new CurrentTenantIdentifierResolverImpl(tenantContext);
    }

    @Bean(name="tenantConnection")
    public MultiTenantConnectionProviderImpl getMultiTenantConnectionProvider(TenantContext tenantContext) {
        return new MultiTenantConnectionProviderImpl(false,tenantContext);
    }

    @Bean
    @Primary
    public PlatformTransactionManager transactionManager(EntityManagerFactory factory,ProducerFactory producerFactory){

        JpaTransactionManager transactionManager = new JpaTransactionManager();
        transactionManager.setEntityManagerFactory(factory);
        KafkaTransactionManager tm = new KafkaTransactionManager(producerFactory);

        return new ChainedKafkaTransactionManager(tm,transactionManager);
    }

    @Bean
    public TenantContext getTenantContext() {
        return new TenantContextImpl();
    }
}

0 个答案:

没有答案