我正在收集有关flush()方法的信息,但我不太清楚何时使用它以及如何正确使用它。据我所知,我的理解是持久化上下文的内容将与数据库同步,即发出未完成的语句或刷新实体数据。
现在我得到了两个实体
A
和
B
的场景(在一对一关系中,但不是由JPA强制执行或建模的)。
A
有一个手动设置的复合PK,也有一个自动生成的身份字段
recordId
。此
recordId
应作为
A
的外键写入实体
B
。我在单个事务中保存
A
和
B
。问题是自动生成的值
A.recordId
在事务中不可用,除非我在
A
上调用
em.persist()
之后显式调用
em.flush()
。(如果我有一个自动生成的身份PK,那么实体中的值将直接更新,但这里不是这种情况。)
在事务中使用
em.flush()
时,
是否会造成任何危害?
发布于 2010-11-25 18:22:33
可能
em.flush()
的确切细节依赖于实现。总之,像Hibernate这样的JPA提供者可以缓存它们应该发送到数据库的SQL指令,通常直到您实际提交事务为止。例如,您调用
em.persist()
,Hibernate记得它必须进行数据库插入,但直到您提交事务时才实际执行指令。Afaik,这主要是出于性能原因。
在某些情况下,无论如何您都希望立即执行SQL指令;通常在需要某些副作用的结果时,比如自动生成的键或数据库触发器。
em.flush()
所做的是清空内部SQL指令缓存,并将其立即执行到数据库中。
归根结底:没有什么坏处,只会对性能造成(轻微)影响,因为您正在覆盖JPA提供者关于向数据库发送SQL指令的最佳时机的决定。
发布于 2018-01-09 03:25:16
实际上,
em.flush()
不仅仅发送缓存的SQL命令。它尝试将持久化上下文同步到底层数据库。如果您的缓存包含要同步的集合,则可能会在您的进程上造成大量时间消耗。
请注意使用它。
发布于 2019-06-12 17:14:11
当在事务中使用em.flush()时,它会造成任何危害吗?
是的,它可能会在数据库中持有锁的持续时间超过必要的时间。
通常,当使用JPA时,您将事务管理委托给容器(也称为CMT -在业务方法上使用@ transaction注解),这意味着事务在进入方法时自动启动,并在结束时提交/回滚。如果让EntityManager处理数据库同步,sql语句的执行将仅在提交之前触发,从而导致数据库中的锁很短。否则,手动刷新的写操作可能会在手动刷新和自动提交之间保留锁,根据剩余的方法执行时间,锁可能会很长。
请注意,某些操作会自动触发刷新:对同一会话执行本机查询(EM状态必须刷新才能被SQL查询访问),使用本机生成的id插入实体(由数据库生成,因此必须触发insert语句,以便EM能够检索生成的id并正确管理关系)
https://stackoverflow.com/questions/4275111
复制相似问题
扫码关注腾讯云开发者
领取腾讯云代金券
Copyright © 2013 - 2025 Tencent Cloud. All Rights Reserved. 腾讯云 版权所有
深圳市腾讯计算机系统有限公司 ICP备案/许可证号: 粤B2-20090059 深公网安备号 44030502008569
腾讯云计算(北京)有限责任公司 京ICP证150476号 | 京ICP备11018762号 | 京公网安备号11010802020287