非冗余休眠列表映射 (OneToMany)

Posted

技术标签:

【中文标题】非冗余休眠列表映射 (OneToMany)【英文标题】:Non-Redundant Hibernate List-Mapping (OneToMany) 【发布时间】:2021-10-16 16:06:54 【问题描述】:

在数据库中有“糕点”。一种糕点含有零种、一种或多种过敏原。

因此,我在 Pastry 中使用具有 @OneToMany 关系的列表。现在,通过这种管理关系的方式,我们得到了多余的条目,因为每个糕点都会创建一个具有相同过敏原的新条目:

我们当前的解决方案如下所示:

这两个数据库表之间的映射表。

如何通过直接引用 Pastry 类列表中的过敏原元素来实现非冗余解决方案?我用谷歌搜索了很多,但遗憾的是找不到任何有用的东西。

看起来像这样:

关于我对解决方案的评论:

【问题讨论】:

忘了补充:理论上我知道数据库是什么样子的,但我不确定如何在 Hibernate 中实现。 【参考方案1】:

您需要的是一个名为JoinTable。根据您的架构定义,这可以作为一个潜在的示例:

@Data
@Entity(name = "Pastry")
@Table(name = "PASTRY")
public class Pastry 

    @Id
    @GeneratedValue(strategy = GenerationType.AUTO)
    private Long id;

    private String name;

    @ManyToMany
    @JoinTable(
        name = "PASTRY_ALLERGEN",
        foreignKey = @ForeignKey(name = "FK_PASTRY_ALLERGEN_PASTRY"),
        inverseForeignKey = @ForeignKey(name = "FK_PASTRY_ALLERGEN_ALLERGEN"),
        joinColumns = @JoinColumn(name = "pastry_id", referencedColumnName = "id"),
        inverseJoinColumns = @JoinColumn(name = "allergen_id", referencedColumnName = "id")
    )
    private Set<Allergen> allergens = new HashSet<>();


对于Pastry 关联和:

@Data
@Entity(name = "Allergen")
@Table(name = "ALLERGEN")
public class Allergen 

    @Id
    @GeneratedValue(strategy = GenerationType.AUTO)
    private Long id;

    private String name;


对于Allergen 关联。

此映射将依次生成一个名为PastryAllergens 的中间表,该表将保存对Pastry 表的PK 和Allergen 表的PK 的引用。

【讨论】:

非常感谢,但这基本上只是第二张图片,无需手动添加,对吧?无论如何,谢谢,我就用这个方法! 我不认为你想做的事情是可能的,至少在关系数据库中是不可能的。您正在处理关系,因此您需要一种存储关系的方法。 还有一件事:当我尝试对不同的糕点使用过敏原两次时,它会抛出异常“重复条目 '1' (allergen_id) for key '...” - 知道如何解决那?我可以在糕点中添加多种过敏原,但不能多次使用过敏原 我在底部的原始问题中放置了我插入语句的图片。绿色突出显示的仍然有效,但第二次使用相同过敏原 ID 的粉红色则不起作用 您能否分享您执行插入的代码以及您获得的堆栈跟踪?

以上是关于非冗余休眠列表映射 (OneToMany)的主要内容,如果未能解决你的问题,请参考以下文章

休眠:覆盖(实体)超类的 OneToMany 映射字段?

JPA(休眠)映射OneToMany不正确?

我在@OneToMany 休眠映射中遇到错误?

@OneToMany 映射休眠中的集合

休眠映射,在未映射的类上

您如何在休眠条件中订购 oneToMany 连接表