【问题标题】:Cannot delete a record with OneToMany relation无法删除具有 OneToMany 关系的记录
【发布时间】:2012-07-04 16:08:28
【问题描述】:

当我删除一个表中的记录时,应该删除另一个表中的相关记录。但我收到了:

java.sql.BatchUpdateException:批处理条目 0 更新 child_table set parent_table_id=null where parent_table_id=63 被中止

上述异常是针对以下设置引发的:

@OneToMany(cascade = javax.persistence.CascadeType.ALL, targetEntity = ChildTable.class)
@JoinColumn(name = "parent_table_id")
@org.hibernate.annotations.Fetch(FetchMode.SUBSELECT)
public List<ChildTable> getTables() {
    return tables;
}

如果我没记错的话,有了这样的注释,当在ParentTable中删除一条记录时,应该在Child one中删除对应关系。在完全删除之前,它会尝试变为“null”(因为相应的记录不再存在)。此 id 列是“非空”。当我将其设为“null”(仅用于测试这种情况)时,一切正常。

你能帮我理解这背后的真正问题吗?

提前谢谢你。

【问题讨论】:

    标签: java hibernate


    【解决方案1】:

    我通常不使用注释。我更喜欢 hbm 映射文件,所以我可以告诉你一些可能的 hbm 映射解决方案。 :) 我认为您需要在父级一对多关系中添加 inverse=true 。 Always put inverse=true in your parent collections。有关 inverse=true 等价的注释,请参阅this

    如果这不起作用,我知道这不是一个好的解决方案,您可以尝试在一对多中使用 not-found="ignore" 或 @NotFound(action=NotFoundAction.IGNORE)父母的关系。最终,它与为数据库中的外键列设置 not-null=false 具有相同的效果。

    【讨论】:

      【解决方案2】:

      其中一位响应者给出了正确答案,但他将其删除。 我不得不使用休眠级联注释而不是 JPA 注释。它对我不起作用,因为问题比仅仅使用 JPA 和休眠注释更深一点。 ChildTable 的映射器类具有 int 类型的 parent_table_id,而不是映射 id 字段的 ParentTable 类类型。所以我将其更改为:

      @Entity
      @Table(name = "child_table")
      public class ChildTable {
      
      private int id;
      private int parent_table_id;
      ...
      

      @Entity
      @Table(name = "child_table")
      public class ChildTable {
      
      private int id;
      private ParentTable parent_table;
      ...
      

      确实进行了一些额外的更改(与此相关)并且删除开始按预期进行。

      因此,如果您在删除一对多关系中的实体时遇到相应错误,并且注释使用情况一切正常,请检查映射器类中的类型和字段:)

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2013-05-22
        • 2020-10-25
        • 1970-01-01
        • 1970-01-01
        • 2016-04-21
        • 1970-01-01
        相关资源
        最近更新 更多