我已经看过很多类似的问题,但它们通常只与我的相关。
这是我的代码。
@Override //class implements interface
//can also add "rollbackFor = OutOfMemoryError.class" here, to no avail
@Transactional(noRollbackFor = IllegalArgumentException.class)
public ReportTemplate getByCode(final String code)
//throws IllegalArgumentException - see question text
{
if(code == null) {
throw new IllegalArgumentException("ss");
}
}
Consumer(非事务性)通过自动连接接口调用此方法。 尽管noRollbackFor事务(仅由此方法组成)得到回滚。 好的我理解那些说"默认情况下它的回滚对于任何未经检查的人,所以由于默认没有被覆盖,该规则仍适用于#34;。但这不应该是真的,因为这意味着noRollbackFor是没用的:)我们可以尝试在上面的评论中指定rollbackFor,希望它会取消"默认" rollbackFor - 但这没有帮助:回滚仍然发生;看起来这个设置只是添加到"默认"。最糟糕的是,当noRollbackFor和rollbackFor覆盖相同的后代异常时(例如,在我的情况下,RuntimeException与IllegalArgumentException,谁赢了?),我无法找到关于它应该如何工作的精确规范。
嗯,我能够找到but one official clarification并且它说"最强的匹配规则获胜" - 但在我看来,这似乎不是普遍适用的。此外,由于某种原因,他们过于具体:他们说no-rollback-for =" InstrumentNotFoundException"从字面上看,除了InstrumentNotFoundException以外的任何例外"会被回滚(但是关于InstrumentNotFoundException' s后代呢?)无论如何它已经过时了:2.5.x,而较新的文档只是说" rollbackFor列出要回滚的异常,以及noRollbackFor以非常矛盾的方式列出了不是"的例外情况,我会说。
更有趣的是,如果我在" throws"中指定IllegalArgumentException,则上面的代码会停止回滚。条款。是的,我没有必要,因为它没有被检查 - 但如果我这样做,noRollbackFor似乎终于注意到它并且行为正常!有谁知道手册说会发生什么?或者它可能是一个错误?
更新 以下是spring事务日志(在我的实际代码中,YargReportTemplateDao $ TemplateNotFoundException到处都有,而不是IllegalArgumentException)
1)" throws"
[qtp22373939-44] TRACE org.springframework.transaction.interceptor.TransactionInterceptor - Completing transaction for [ru.it.p321.dao.YargReportTemplateDaoImpl.getByCode] after exception: ru.it.p321.dao.YargReportTemplateDaoImpl$1: Yarg template was not found for given code: ITORG_REJECT_NOTIFICATION
[pool-28-thread-1] DEBUG org.springframework.transaction.jta.JtaTransactionManager - Initiating transaction commit
[qtp22373939-44] TRACE org.springframework.transaction.interceptor.RuleBasedTransactionAttribute - Applying rules to determine whether transaction should rollback on ru.it.p321.dao.YargReportTemplateDaoImpl$1: Yarg template was not found for given code: ITORG_REJECT_NOTIFICATION
[qtp22373939-44] TRACE org.springframework.transaction.interceptor.RuleBasedTransactionAttribute - Winning rollback rule is: NoRollbackRuleAttribute with pattern [ru.it.p321.dao.YargReportTemplateDao$TemplateNotFoundException]
2)没有"抛出
[qtp21176461-48] TRACE org.springframework.transaction.interceptor.TransactionInterceptor - Completing transaction for [ru.it.p321.dao.YargReportTemplateDaoImpl.getByCode] after exception: org.springframework.dao.InvalidDataAccessApiUsageException: Yarg template was not found for given code: ITORG_REJECT_NOTIFICATION; nested exception is ru.it.p321.dao.YargReportTemplateDaoImpl$1: Yarg template was not found for given code: ITORG_REJECT_NOTIFICATION
[qtp21176461-48] TRACE org.springframework.transaction.interceptor.RuleBasedTransactionAttribute - Applying rules to determine whether transaction should rollback on org.springframework.dao.InvalidDataAccessApiUsageException: Yarg template was not found for given code: ITORG_REJECT_NOTIFICATION; nested exception is ru.it.p321.dao.YargReportTemplateDaoImpl$1: Yarg template was not found for given code: ITORG_REJECT_NOTIFICATION
[qtp21176461-48] TRACE org.springframework.transaction.interceptor.RuleBasedTransactionAttribute - Winning rollback rule is: null
[qtp21176461-48] TRACE org.springframework.transaction.interceptor.RuleBasedTransactionAttribute - No relevant rollback rule found: applying default rules
答案 0 :(得分:2)
您看到的行为与事务处理无关,但具有异常转换。默认情况下,当使用@Repository
注释类时,Spring将注册PersistenceExceptionTranslationInterceptor
,这会将异常转换为Spring DataAccessException
之一。默认情况下,它会转换所有异常,除非在throws子句中声明了抛出的异常。
此异常转换发生在TransactionInterceptor
之前,并且这种情况从未抛出IllegalArgumentException
因为已经转换为其他内容。
答案 1 :(得分:0)
创建您获胜的自定义异常(从exception扩展),然后为您应用noRollBackFor自定义异常类