使用Bitronix Transcation Manager时,将Hibernate after_transaction设置为JTA连接释放模式是否安全?

Vla*_*cea 5 hibernate transactions xa distributed-transactions bitronix

根据Hibernate文档,在JTA环境中,默认的连接释放模式是after_statement,这意味着在每个语句之后释放hibernate逻辑连接.

释放逻辑连接后,将调用Connection close()方法,并从事务管理器中取消列出当前资源.

根据RedHat 交易开发者指南:

"delistResource方法用于将指定资源与目标对象中的事务上下文分离.应用程序服务器使用两个参数调用该方法:

An XAResources object, which represents the resource.
A flag to indicate whether the operation is due to the transaction being suspended (TMSUSPEND), a portion of the work has failed (TMFAIL), or a normal resource release by the application (TMSUCCESS)."
Run Code Online (Sandbox Code Playgroud)

由于Bitronix使用TMSUCCESS:

 currentTransaction.delistResource(xaResourceHolderState.getXAResource(), XAResource.TMSUCCESS);
Run Code Online (Sandbox Code Playgroud)

这意味着连接与当前事务分支取消关联,有时您可能最终为同一资源适配器争用2个不同的连接.

我认为保持连接的次数与事务一样多是一个更好的选择,因为我们通常每个事务执行多个语句.所以after_transaction释放模式听起来更有吸引力.

使用Bitronix,after_transaction释放模式更合适吗?有没有人在生产环境中体验过它?

小智 6

你不应该看到after_statement和after_transaction之间有任何区别,至少与BTM有关.从理论上讲,after_statement"更正确",因为连接和事务在XA上下文中应该完全独立,并且连接应该能够同时为多个事务服务.在实践中,连接和事务几乎从不是独立的,因为几乎没有资源支持这一点.

BTM连接池实现了一个相对复杂的FSM,允许它在连接上保持事务隔离,同时在可能的情况下重新使用连接.

在单个事务的上下文中,重复从池中获取连接然后关闭它应该只从池中使用一个连接:同一个连接应始终由池保留并重新使用.我能想到的唯一原因是,如果你在第一个连接尚未关闭的情况下再次获得连接,则会导致从池中消耗两个连接.任何其他原因都可能被视为BTM连接池中的错误.