由于我们的系统架构,我正在尝试实施客户端编排策略(ibm-client-orchestration)。我们使用的是实际编排一些Web服务的集成层。在单个工作单元中调用Web服务,并委托使用Spring框架的业务层。一个例子是这样的:
UserTransaction ut = getUserTransaction()
ut.begin();
// insert data, will be delegated to some jpa repository
service1.saveData(data)
// find data inserted above
service2.findData(data)
ut.commit();
在上面提到的链接中,作者建议在查找时使用传播强制保存和传播SUPPORTS,它将尝试在事务日志中查找数据。不知何故,我不知道在给定上述场景的情况下,我无法在查找步骤中找到插入的数据。以下是一些可能有用的有用信息:
Entity Manger Factory取自LocalContainerEntityManagerFactoryBean,并使用具有以下属性的Hibernate JPA Vendor:
jpaProperties.setProperty( “hibernate.hbm2ddl.auto”, environment.getRequiredProperty( “entitymanagerfactory.hibernate.hbm2ddl.production”)); jpaProperties.setProperty(“hibernate.connection.autocommit”,“false”); jpaProperties.setProperty(“hibernate.transaction.jta.platform”,“org.hibernate.service.jta.platform.internal.WebSphereJtaPlatform”); jpaProperties.setProperty(“hibernate.transaction.manager_lookup_class”,“org.hibernate.transaction.WebSphereExtendedJTATransactionLookup”);
我没有在Websphere中配置任何JPA Provider,所以应该是它的默认实现。
我提到如果我在委托DAO层,jpa存储库中的saveAndFlush()方法中使用,我能够找到,但我不会使用它并使用事务传播。
transactionManager bean的定义:
@Bean
public PlatformTransactionManager transactionManager() {
JtaTransactionManager txManager = new JtaTransactionManager();
txManager.afterPropertiesSet();
return txManager;
}
@Bean
public EntityManagerFactory entityManagerFactory() {
// hibernate vendor
HibernateJpaVendorAdapter vendorAdapter = new HibernateJpaVendorAdapter();
vendorAdapter.setDatabase(databaseType());
vendorAdapter.setGenerateDdl(true);
// compose entityManager
LocalContainerEntityManagerFactoryBean factoryBean = new LocalContainerEntityManagerFactoryBean();
factoryBean.setJpaVendorAdapter(vendorAdapter);
factoryBean.setDataSource(datasource());
factoryBean.setJtaDataSource(datasource());
// scan packages
factoryBean.setPackagesToScan(environment.getRequiredProperty("entitymanager.scan.packages"));
// JPA properties
factoryBean.setJpaProperties(getEntityManagerFactoryJpaProperties());
factoryBean.afterPropertiesSet();
return factoryBean.getObject();
}
任何建议都表示赞赏。 感谢。
答案 0 :(得分:0)
对于初学者,您应该使用特定于网络的JtaTransactionManager
而不是通用的。我建议使用tag which detects which specific or generic one to use. So basically replace your definition of the
JtaTransactionManager`和以下内容:
<tx:jta-transaction-manager />
接下来,您的代码不使用spring事务管理,但是普通JTA事务使用注释来驱动事务(@Transactional
与<tx:annotation-driven />
或使用注入PlatformTransactionManager
来启动和提交事务
TransactionStatus txStatus = getTransactionManager().getTransaction(null);
// insert data, will be delegated to some jpa repository
service1.saveData(data)
// find data inserted above
service2.findData(data)
getTransactionManager().commit(txStatus);
另请参阅the reference guide了解其他方法和更多信息。
在LocalContainerEntityManagerFactoryBean
中确保注入jtaDataSource
属性而不是dataSource
属性,这将触发一些其他设置。
@Bean
public FactoryBean<EntityManagerFactory> entityManagerFactory() {
LocalContainerEntityManagerFactoryBean lcemfb = new LocalContainerEntityManagerFactoryBean();
lcemfb.setJtaDataSource(dataSource());
// .... Other properties
return lcemfb;
}
关于你的hibernate配置的另一个注意事项,hibernate.connection.*
属性由于数据源的注入而无用,你不需要hibernate.transaction.manager_lookup_class
因为(或者至少应该)已经覆盖按配置的JtaPlatform
。