JPA 同步实体访问器
Posted
技术标签:
【中文标题】JPA 同步实体访问器【英文标题】:JPA synchronizing entity accessors 【发布时间】:2010-09-24 04:53:32 【问题描述】:设置如下:实体类包含其他延迟加载的实体的集合。诀窍是,我需要执行一些与数据相关的工作(例如,我想用集合的元素计算某些校验和)。
这里的诀窍是我想不惜一切代价避免竞争条件,例如:“有人在我进行数据计算时更新了实体”。在正常情况下,我只会声明 getter/setter 同步并且会很高兴。但据我了解,如果另一个线程决定从数据库更新实体状态,而我正在计算校验和,它将完全忽略“同步”方法(它将直接访问该字段)。
我可能错了。所以问题是:在初始校验和计算时,有没有办法“锁定”对实体部分或整个实体本身的访问?
提前致谢! 附:如果您需要代码 sn-p 来说明问题 - 请告诉我。到目前为止,我认为这个问题很清楚。
【问题讨论】:
【参考方案1】:我可能错了。所以问题是:在初始校验和计算时,有没有办法“锁定”对实体部分或整个实体本身的访问?
JPA 2.0 支持 pessimistic concurrency 并且您可以读取实体并在数据库级别锁定相应的行(请注意,提到的链接早于 JPA 2.0 规范的最终版本,并没有反映所有可能的值LockMode
枚举,但你明白了)。
如果您使用的是 JPA 1.0,恐怕您将不得不使用本机 SQL 来执行等效的 SELECT ... FOR UPDATE
。
参考文献
JPA 2.0 规范 第 3.4.4 节“锁定模式”【讨论】:
拜托,我正在使用 JPA 2.0 Toplink 实现。无论如何,谢谢你的回答。 @Juriy 我会(稍后)。同时,下载规范并阅读我提到的部分将是一个非常好的主意 :) PS:我猜你的意思是 EclipseLink,TopLink 是 JPA 1.0 实现。 谢谢,我想我可以做到这一点。基本上我现在的主要问题是我认为我正在使用 JPA 2.0 而它是 1.0... @Juriy 然后你必须使用原生查询和SELECT ... FOR UPDATE
【参考方案2】:
您还可以在实体的属性上使用@Version(适用于 JPA 1.0)
http://java.dzone.com/articles/jpa-20-concurrency-and-locking
【讨论】:
那是乐观锁定。这可能不是@Juriy 想要的,因为它将允许操作继续进行,但如果对象被另一个事务更改,则提交将失败。以上是关于JPA 同步实体访问器的主要内容,如果未能解决你的问题,请参考以下文章