gpt4 book ai didi

java - 关于Spring事务管理重新设计的建议

转载 作者:行者123 更新时间:2023-12-01 05:03:11 25 4
gpt4 key购买 nike

我将尝试描述我正在尝试解决的问题。我意识到我开发的一个应用程序的 Spring 事务管理实现得不好。我使用声明性方法来处理在 DAO 接口(interface)方法 (CRUD) 上定义的事务,而不是在服务层方法上定义的事务。它是一个 Web 应用程序,可以进行某种消息处理,并且多个线程同时对同一消息实例进行操作。以下是典型顺序中的步骤:

  1. 消息在 T1(事务 1)中创建并放入出站队列中。 T1 已终止。
  2. 消息由不同的线程从队列中取出,发送并更新发送时间和一些附加信息。设置消息对象的属性并调用 dao.update(m),t2 开始。
  3. 在 t2 提交之前,收到传送报告,Tread3 开始处理相同的消息对象,方法是在数据库中查找它(在步骤 1 中保存),更新其状态属性并调用 dao.upate(m),以便 t3 在 t2 仍在运行时启动进行中。
  4. 另一个线程(线程 4)通过在 t4 中再次更改其状态来进一步处理同一消息对象。

时不时发生的结果是从 t2 开始的更改丢失,并且 db 中的发送时间为空。我需要帮助弄清楚如何改进应用程序设计并通过防止同一消息的并发处理来消除此问题。

  1. 我应该专注于事务重新设计(在服务级别而不是 dao 上使用它)并使用可序列化隔离级别(或其他)还是

  2. 我应该使用 JPA 实体管理器锁定吗?

应用程序使用 spring 3 和 JPA2 以及 hibernate 实现。

最佳答案

是的,我会将事务移至服务级别,但我会重新考虑整个设计,看看是否可以将整个过程放入一个线程中。如果我没记错的话,Spring 的事务管理是基于线程的 - 我怀疑您是否能够拥有跨线程的事务。

此外,如果可能的话,请尝试简化事情,以便您只访问数据库一次。如果您确实需要四个单独的更新,请在同一线程的同一事务中按顺序运行它们。否则,您将无法顺利完成交易。

显式锁定也会造成巨大的伤害 - 这样做很可能会导致死锁。

编辑:回应OP的评论:

我建议找到一种方法将 T3 更新与 T2 更新分开,并让 T2 事务在进行 T3 更新之前提交。

也许将传送报告放入消息队列中。然后提出一个策略,在 T3 中查找该项目,如果存在则进行更新,如果不存在则稍后重试。

如果您知道收到送达报告和 T2 事务结束之间存在最短或平均时间,也许您可​​以在送达收据的处理中加入该延迟时间以创建 T3 更新。

关于java - 关于Spring事务管理重新设计的建议,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/13100536/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com