JPA-@ManyToMany双向关系,删除了反向的实体,并在JoinTable中错误处理了剩余关系



我在JPA中定义了两个实体:员工技能

此实体之间定义了关系@ManyToMany

public class Employee { 
     @ManyToMany(fetch = FetchType.LAZY)
     @JoinTable(name = "employee_skill",
        joinColumns = @JoinColumn(name = "employee_id"),
        inverseJoinColumns = @JoinColumn(name = "skill_id")
     )
     private Set<Skill> skills = new HashSet<>();
}
public class Skill { 
     @ManyToMany(mappedBy = "skills", fetch = FetchType.LAZY)
     private Set<Employee> skilledEmployees = new HashSet<>(); 
}

现在我有这样的问题:如果我使用实体管理器移除技能实体。它删除了ok。但在数据库employee_skill@JoinTable中,仍然存在与此已删除实体(其id)的关联。

当我移除技能时,我不想移除Employee,因此所有级联移除或orfanRemove在这里都没有用处。

我想知道为什么这种关系并没有自动从数据库中删除。当联接表中的此关联保留时,它会给我javax.persistence.EntityNotFoundException:找不到

因此,在删除技能实体之前,我可以手动删除这些关联。但这真的是最好的做法吗?

删除@ManyToMany双向关系中的实体的最佳做法是什么?删除Employee或Skill这样的实体时,不应该影响另一个实体吗

由于Employee是关系的拥有方(基于您的mappedBy值),对其与Skill对象关系的任何更新都将更新数据库关联。这是拥有方的责任,它会履行这一职责。但另一种方式是不会发生的。您可能的解决方案之一是手动定义数据库cascade规则,类似于联接表中的以下内容:

FOREIGN KEY (skill_id) REFERENCES skills (id)
  MATCH SIMPLE ON UPDATE CASCADE ON DELETE CASCADE

这样,对Skills的任何更新都会更新数据库中的关联。

另一种方法是通过在Employee中定义mappedBy来将拥有方更改为Skill,基于Employee/Skill的刻板关系,这并不自然。

最新更新