【问题标题】:Hibernate Batch insert/update constraintviolationexceptionHibernate Batch 插入/更新约束违反异常
【发布时间】:2012-06-25 10:15:13
【问题描述】:

我正在编写一个程序来对数十万个相关类型的实体运行批处理。我最初是通过每个持久化的单个事务来执行此操作的。这看起来很慢,所以我尝试按照http://docs.jboss.org/hibernate/core/3.3/reference/en/html/batch.html 中描述的方式进行一些幼稚的批量更新,使用更长的事务和偶尔的刷新+清除。我的某些实体类型遇到了 ConstraintViolationException,因为我有唯一的字段约束。但是,我不确定如何检查现有实例;我目前有一个列出冲突的标准,但它似乎没有返回我在同一事务中保存或更新的实体。

一个虚构的例子可能会有所帮助:
实体 家庭、人、姓名
家庭有很多人(一对多)
人有很多名字,不同的人可以有相同的名字。 (多对多)

我的更新包括保留一个家庭及其人员和名称,但我不确定如何对名称进行重复数据删除(可能与数据库中的现有名称或同一更新批次中的另一个名称冲突)。我可以在休眠之外跟踪新实体的唯一约束字段,但我认为这可能没有必要。是否有任何内置方法可以检查数据库中的重复项和未提交的更改?我看到了Hibernate batch updates with constraintviolationexception,但我不喜欢在正常代码路径中使用异常。谢谢,我感谢任何指导。

【问题讨论】:

    标签: hibernate batch-processing


    【解决方案1】:

    简短的回答:不。对于批处理操作,Hibernate 不会跟踪生成的 ID,因此,您必须访问每个 Name 的数据库,因为您将根据名称而不是 ID 进行查询,除非您正在使用一些查询缓存(我想这对您的情况来说会很棘手)。

    我建议分两步(三步?)执行此操作:首先,批量插入所有 Name 对象。然后,使用 Hibernate 本身加载它们,将它们存储在 Map 上。然后,只需持久化其他数据,将Name 链接到非持久化Person。当然,你需要和名字一样多的内存 :-) 但是你为什么要把Name 作为一个单独的实体呢?

    【讨论】:

    • 感谢您的回复。是的,我想以一种或另一种方式,我需要在休眠之外有一个映射,键控每个实体的唯一约束元组,至少每批。我的意思是 Name 只是一个说明,在我的实际应用程序/模式/实体中,多对多关系更有意义。
    猜你喜欢
    • 2014-10-08
    • 2021-12-05
    • 1970-01-01
    • 1970-01-01
    • 2012-07-15
    • 1970-01-01
    • 2011-01-27
    • 1970-01-01
    • 2020-04-01
    相关资源
    最近更新 更多