微信公众号搜"智元新知"关注
微信扫一扫可直接关注哦!

无法删除父实体,因为在双向映射的情况下子引用 Parent.java Child.java ChildIdentifier.java

如何解决无法删除父实体,因为在双向映射的情况下子引用 Parent.java Child.java ChildIdentifier.java

正如我在标题中提到的那样,当我尝试删除“父”实体时,由于其子代引用由于数据完整性违规而遇到麻烦。我以为该错误与实体的某些缺少配置有关,但是我无法获取缺少的东西。 是否可以让Hibernate / JPA理解先删除子级引用,然后再删除父级引用?我想继续使用这种关系和Spring Data JPA存储库。

如果JPA / Hibernate有可能,我想避免通过显式使用实体管理器来处理这些情况(因此,我不想“手动”删除它们),因为通过自动查询生成的Spring JPA是极大地帮助了所有“选择/计数/ ..”案件。

父母与子女的关系在双方都映射,其中:

  1. 父级不拥有某列,因此映射由“ mappedBy”配置
  2. 子级有一个复合键,其中一列通过其ID链接到父级
  3. 通过JPA注释进行配置

在休眠状态下执行查询时,无法找到某些具有要删除记录的外键约束的子项,因此它想先执行“父删除”,然后再移至“子项”

原因是:

违反参照完整性约束:“ FK_PARENT_ID_PARENT:PUBLIC.CHILD外键(PARENT_ID)引用PUBLIC.PARENT(ID)(1)”; sql语句: 从父母那里删除id =? [23503-200]

数据库表是由外部sql脚本创建的,并且将hibernate配置为避免生成ddl。这是一项要求,无法修改,因此无法删除子表中的外键和id约束。

在下面您可以找到实体的Java定义,在这里我尝试概述配置。

父实体与@p拥有一个@OnetoMany

  • mappedBy =子字段的名称
  • fetch = FetchType.EAGER
  • cascade = CascadeType.ALL
  • orphanRemoval = true

子实体拥有@ManyToOne加@JoinColumn,其中:

  • optional = false
  • name =表列的名称

下面的Java代码

Parent.java

public static Font createFont(final String family,final int style,final int size) {
    return new NonUIResourceFont(StyleContext.getDefaultStyleContext().getFont(family,style,size));
}

public static class NonUIResourceFont extends Font {

    public NonUIResourceFont(final Font font) {
        super(font);
    }
}

Child.java

import javax.persistence.CascadeType;
import javax.persistence.Column;
import javax.persistence.Entity;
import javax.persistence.FetchType;
import javax.persistence.Id;
import javax.persistence.OnetoMany;
import java.util.Objects;
import java.util.Set;

@Entity
public class Parent {
    @Id
    @Column
    private long id;

    @Column
    private String name;

    @OnetoMany(mappedBy = "parent",fetch = FetchType.EAGER,cascade = CascadeType.ALL,orphanRemoval = true)
    private Set<Child> children;

    public long getId() {
        return id;
    }

    public void setId(long id) {
        this.id = id;
    }

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }

    public Set<Child> getChildren() {
        return children;
    }

    public void setChildren(Set<Child> children) {
        this.children = children;
    }

    @Override
    public boolean equals(Object o) {
        if (this == o) return true;
        if (o == null || getClass() != o.getClass()) return false;
        Parent parent = (Parent) o;
        return id == parent.id;
    }

    @Override
    public int hashCode() {
        return Objects.hash(id);
    }
}

ChildIdentifier.java

import javax.persistence.CascadeType;
import javax.persistence.Column;
import javax.persistence.Entity;
import javax.persistence.Id;
import javax.persistence.IdClass;
import javax.persistence.JoinColumn;
import javax.persistence.ManyToOne;
import java.util.Objects;

@Entity
@IdClass(ChildIdentifier.class)
public class Child {
    @Id
    @Column
    private long id;

    @Column
    private String name;

    @Id
    @JoinColumn(nullable = false,name ="parent_id",referencedColumnName = "id")
    @ManyToOne(optional = false)
    private Parent parent;

    public long getId() {
        return id;
    }

    public void setId(long id) {
        this.id = id;
    }

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }

    public Parent getParent() {
        return parent;
    }

    public void setParent(Parent parent) {
        this.parent = parent;
    }

    @Override
    public boolean equals(Object o) {
        if (this == o) return true;
        if (o == null || getClass() != o.getClass()) return false;
        Child child = (Child) o;
        return id == child.id &&
                Objects.equals(parent,child.parent);
    }

    @Override
    public int hashCode() {
        return Objects.hash(id,parent);
    }
}

版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。