Spring Boot通过使用Atomikos嵌入式事务管理器支持跨多个XA资源的分布式JTA事务。还提供了不支持使用Bitronix嵌入式事务管理器的支持,但在将来的版本中将删除该支持。部署到合适的Java EE应用程序服务器时,还支持JTA事务。
当检测到JTA环境时,JtaTransactionManager将使用Spring来管理事务。自动配置的JMS,DataSource和JPA Bean已升级为支持XA事务。您可以使用标准Spring习惯用法(例如@Transactional)来参与分布式事务。如果您在JTA环境中,但仍要使用本地事务,则可以将spring.jta.enabled属性设置false为禁用JTA自动配置。

19.1 使用Atomikos交易管理器

Atomikos是一种流行的开源事务管理器,可以嵌入到您的Spring Boot应用程序中。您可以使用spring-boot-starter-jta-atomikos入门程序来引入适当的Atomikos库。Spring Boot自动配置Atomikos,并确保将适当的depends-on设置应用于您的Spring Bean,以正确启动和关闭命令。
默认情况下,Atomikos事务日志写入transaction-logs应用程序主目录中的目录(应用程序jar文件所在的目录)。您可以通过spring.jta.log-dirapplication.properties文件中设置属性来自定义此目录的位置。以开头的属性spring.jta.atomikos.properties也可以用于自定义Atomikos UserTransactionServiceImp。有关完整的详细信息,请参见AtomikosPropertiesJavadoc

为了确保多个事务管理器可以安全地协调同一资源管理器,必须为每个Atomikos实例配置一个唯一的ID。默认情况下,此ID是运行Atomikos的计算机的IP地址。为确保生产中的唯一性,应spring.jta.transaction-manager-id为应用程序的每个实例为属性配置一个不同的值。

19.2 使用Bitronix交易管理器

从Spring Boot 2.3开始,对Bitronix的支持已被弃用,并将在以后的版本中删除。

您可以使用spring-boot-starter-jta-bitronix启动器将适当的Bitronix依赖项添加到项目中。与Atomikos一样,Spring Boot自动配置Bitronix并对您的bean进行后处理,以确保启动和关闭顺序正确。
默认情况下,Bitronix事务日志文件(part1.btmpart2.btm)被写入transaction-logs应用程序主目录中的目录。您可以通过设置spring.jta.log-dir属性来自定义此目录的位置。以开头的属性spring.jta.bitronix.properties也绑定到bitronix.tm.ConfigurationBean,从而可以进行完全自定义。有关详细信息,请参见Bitronix文档

为了确保多个事务管理器可以安全地协调同一资源管理器,必须为每个Bitronix实例配置唯一的ID。默认情况下,此ID是运行Bitronix的计算机的IP地址。为确保生产中的唯一性,应spring.jta.transaction-manager-id为应用程序的每个实例为属性配置一个不同的值。

19.3 使用Java EE托管事务管理器

如果将Spring Boot应用程序打包为warear文件,并将其部署到Java EE应用程序服务器,则可以使用应用程序服务器的内置事务管理器。Spring Boot尝试通过查看常见的JNDI位置(java:comp/UserTransactionjava:comp/TransactionManager等)来自动配置事务管理器。如果使用应用程序服务器提供的事务服务,通常还需要确保所有资源都由服务器管理并通过JNDI公开。Spring Boot尝试通过ConnectionFactory在JNDI路径(java:/JmsXAjava:/XAConnectionFactory)中查找来尝试自动配置JMS ,您可以使用该spring.datasource.jndi-name属性来配置DataSource

19.4 混合XA和非XA JMS连接

使用JTA时,主要的JMS ConnectionFactoryBean可识别XA,并参与分布式事务。在某些情况下,您可能想通过使用非XA处理某些JMS消息ConnectionFactory。例如,您的JMS处理逻辑可能需要比XA超时更长的时间。
如果要使用非XA ConnectionFactory,则可以注入nonXaJmsConnectionFactorybean而不是@Primary jmsConnectionFactorybean。为了保持一致性,jmsConnectionFactory还使用bean别名提供了bean xaJmsConnectionFactory
以下示例显示了如何注入ConnectionFactory实例:

  1. // Inject the primary (XA aware) ConnectionFactory
  2. @Autowired
  3. private ConnectionFactory defaultConnectionFactory;
  4. // Inject the XA aware ConnectionFactory (uses the alias and injects the same as above)
  5. @Autowired
  6. @Qualifier("xaJmsConnectionFactory")
  7. private ConnectionFactory xaConnectionFactory;
  8. // Inject the non-XA aware ConnectionFactory
  9. @Autowired
  10. @Qualifier("nonXaJmsConnectionFactory")
  11. private ConnectionFactory nonXaConnectionFactory;

19.5 支持替代嵌入式事务管理器

XAConnectionFactoryWrapperXADataSourceWrapper接口可用于支持替代嵌入式事务经理。这些接口负责包装XAConnectionFactoryXADataSourcebean,并将它们作为常规ConnectionFactoryDataSourcebean公开,它们透明地注册到分布式事务中。数据源和JMS自动配置使用JTA变体,前提是您拥有一个JtaTransactionManagerBean并在其中注册了适当的XA包装器Bean ApplicationContext
AtomikosXAConnectionFactoryWrapperAtomikosXADataSourceWrapper提供了如何编写XA包装很好的例子。