回滚声明式事务
上一节概述了如何在应用程序中以声明方式为类(通常是服务层类)指定事务设置的基础知识。本节描述如何以 XML 配置中简单、声明式的方式控制事务的回滚。有关使用 @Transactional 注解以声明方式控制回滚语义的详细信息,请参阅 @Transactional 设置。
向 TODAY Framework 的事务基础设施指示事务工作要回滚的推荐方法是从当前在事务上下文中执行的代码中抛出 Exception。TODAY Framework 的事务基础设施代码会捕获任何未处理的 Exception,因为它会冒泡调用堆栈,并确定是否将事务标记为回滚。
在其默认配置中,TODAY Framework 的事务基础设施代码仅在运行时、未检查异常的情况下将事务标记为回滚。也就是说,当抛出的异常是 RuntimeException 的实例或子类时。(默认情况下,Error 实例也会导致回滚)。
从事务方法抛出的检查异常在默认配置中不会导致回滚。您可以通过指定 回滚规则 来确切配置哪些 Exception 类型将事务标记为回滚,包括检查异常。
|
回滚规则
回滚规则确定当抛出给定异常时是否应回滚事务,规则基于异常类型或异常模式。 回滚规则可以通过 当使用异常类型定义回滚规则时,该类型将用于匹配抛出的异常及其超类型的类型, 从而提供类型安全性并避免在使用模式时可能发生的任何意外匹配。 当使用异常模式定义回滚规则时,模式可以是完全限定的类名或异常类型(必须是
|
以下 XML 代码片段演示了如何通过 rollback-for 属性提供 异常模式 来为已检查的、特定于应用程序的 Exception 类型配置回滚:
<tx:advice id="txAdvice" transaction-manager="txManager">
<tx:attributes>
<tx:method name="get*" read-only="true" rollback-for="NoProductInStockException"/>
<tx:method name="*"/>
</tx:attributes>
</tx:advice>
如果您不希望在抛出异常时回滚事务,您还可以指定“不回滚”规则。以下示例告诉 TODAY Framework 的事务基础设施即使面对未处理的 InstrumentNotFoundException 也要提交伴随的事务:
<tx:advice id="txAdvice">
<tx:attributes>
<tx:method name="updateStock" no-rollback-for="InstrumentNotFoundException"/>
<tx:method name="*"/>
</tx:attributes>
</tx:advice>
当 TODAY Framework 的事务基础设施捕获异常并咨询配置的回滚规则以确定是否将事务标记为回滚时,最强的匹配规则获胜。因此,在以下配置的情况下,除 InstrumentNotFoundException 之外的任何异常都会导致伴随事务的回滚:
<tx:advice id="txAdvice">
<tx:attributes>
<tx:method name="*" rollback-for="Throwable" no-rollback-for="InstrumentNotFoundException"/>
</tx:attributes>
</tx:advice>
您还可以以编程方式指示所需的回滚。虽然很简单,但此过程具有很强的侵入性,并且将您的代码紧密耦合到 TODAY Framework 的事务基础设施。以下示例显示了如何以编程方式指示所需的回滚:
-
Java
public void resolvePosition() {
try {
// 一些业务逻辑...
} catch (NoProductInStockException ex) {
// 以编程方式触发回滚
TransactionAspectSupport.currentTransactionStatus().setRollbackOnly();
}
}
强烈建议您尽可能使用声明式方法进行回滚。如果您绝对需要,可以使用编程式回滚,但它的使用与实现干净的基于 POJO 的架构背道而驰。