2

这是一个相当理论的问题:

在我的服务类中,如果由于任何原因无法执行操作,即使原因是错误输入或任何其他预期和检查的情况,我也倾向于始终进行回滚。

在使用 Open Session in View 模式 (OSIV) 的 Web 应用程序中,这具有令人讨厌的副作用,即会话关闭并且任何后续延迟加载操作都会失败。我必须编写丑陋的管道代码,以便仅在请求期间的某个时间点发生错误时在请求结束时回滚会话。

这让我开始思考:如果真的出了问题,回滚是否应该是一种特殊的措施?如果不满足条件,服务方法是否必须自己确保不写入/更改数据?输入验证成功但服务方法判定所选输入非法时,前端层更新模型对象(如表单)的情况如何处理?例如,当没有完成回滚时,Hibernate 会在默认配置中自动保留这些更改。

期待您的意见和建议!

4

1 回答 1

2

在我看来,最好以相反的方式思考:首先你得到你的错误条件(这可能导致异常或者它可能导致只返回 null),然后你决定在这种错误情况下回滚是否有用.

一个非常重要的问题是:谁在做事务处理?它是由您的服务的调用者完成的,还是在服务本身中完成的(这意味着,每个服务调用都是它自己的事务)。

A)调用者正在处理事务:
那么服务几乎不应该进行回滚,因为它还会回滚调用者在调用此服务之前所做的其他语句。调用者可能会将服务的错误视为正常情况并继续。在这种情况下,不会丢失任何数据库语句。如果调用者在错误后无法继续,则回滚事务是调用者的工作。
这意味着服务不能将不完整的数据写入数据库,并且必须在写入之前检查可能的错误情况。
在两种情况下,服务中的回滚仍然是有用
的: - 错误情况肯定是编程错误的结果。
- 在不回滚的情况下处理错误情况在服务中需要付出很多努力。在这种情况下,在 Javadoc 中记录回滚条件非常重要,因为调用者必须注意它。

B) 服务正在处理事务。每个服务调用都是它自己的事务:
该服务可以自由地随意回滚。如果服务首先检查条件并且不写入数据或者如果它执行回滚,则结果是相同的并且对调用者不可见。如果写入数据,服务必须执行提交或回滚。如果它抛出异常,强烈建议回滚,因为调用者不希望在这种情况下写入数据。

顺便说一句,如果在 Session 对象中抛出异常,Hibernate 会自动回滚。

于 2012-03-14T11:04:27.437 回答