持久性单元作为RESOURCE_LOCAL还是 JTA?

2022-08-31 10:21:18

我有以下疑问:

  1. 这两者之间有什么区别?
  2. 是否所有数据库都支持这两种功能?
  3. JPA TransactionManager 和 JTA TransactionManager 有什么不同吗?

答案 1

JPA 实现可以选择自己管理事务 (),也可以选择由应用程序服务器的 JTA 实现来管理事务。RESOURCE_LOCAL

在大多数情况下,RESOURCE_LOCAL是可以的。这将使用基本的 JDBC 级事务。缺点是事务是 JPA 持久性单元的本地事务,因此,如果您想要跨多个持久性单元(或其他数据库)的事务,那么RESOURCE_LOCAL可能不够好。

JTA还用于管理JMS和JCA等系统之间的事务,但对于我们大多数人来说,这是相当奇特的用法。

要使用 JTA,您需要在应用程序服务器中支持它,还需要 JDBC 驱动程序的支持。


答案 2

作为其他答案的补充

以下是非常有用的文章(发表在Apache TomEE网站上)的摘录,这也可以帮助回答OP的第一个问题(文章的链接如下)。


比较RESOURCE_LOCAL和 JTA 持久性上下文


使用<生存单位事务类型=“RESOURCE_LOCAL”>负责EntityManager(PersistenceContext/Cache)创建和跟踪...

  • 您必须使用 EntityManagerFactory 来获取 EntityManager
  • 生成的 EntityManager 实例 PersistenceContext/Cache
  • EntityManagerFactory只能通过@PersistenceUnit注释注入(不能@PersistenceContext)
  • 不允许使用@PersistenceContext来指代RESOURCE_LOCAL
  • 您必须使用 EntityTransaction API 在每次调用 EntityManger 时开始/提交
  • 调用 entityManagerFactory.createEntityManager() 两次会导致个单独的 EntityManager 实例,从而产生个单独的 PersistenceContexts/Caches。
  • 使用多个 EntityManager 实例几乎从来都不是一个好主意(除非您销毁了第一个实例,否则不要创建第二个实例)


使用<persistence-unit transaction-type=“JTA”> CONTAINER将执行EntityManager(PersistenceContext/Cache)创建和跟踪...

  • 不能使用 EntityManagerFactory 来获取 EntityManager
  • 您只能获取容器提供的实体管理器
  • 实体管理器只能通过@PersistenceContext注释注入(不能@PersistenceUnit)
  • 不允许使用@PersistenceUnit来引用 JTA 类型的单位
  • 容器给出的 EntityManager 是对与 JTA 事务关联的持久性上下文/缓存的引用
  • 如果没有正在进行的 JTA 事务,则无法使用 EntityManager,因为没有 PersistenceContext/Cache。
  • 在同一事务中,每个具有对同一单元的 EntityManager 引用的人都将自动引用相同的 PersistenceContext/Cache
  • 持久性上下文/缓存在 JTA 提交时刷新并清除

任何有兴趣学习Java Persistence API的人 - 请帮自己一个忙,并在这里阅读完整的文章:JPA Concepts:JPA 101


推荐