HQL从多对多的映射中删除关联

时间:2012-11-08 15:42:12

标签: java hibernate jpa primefaces hql-delete

我有两个实体CRImageType& CRVariable与多对多关系如下:

CRImageType实体:

@Entity
@Table(name = "imageviewer_crimagetype")
public class CRImageType implements Serializable   {
    private static final long serialVersionUID = 1L;

    @Id
    @GeneratedValue
    @Column(name = "ImTypeId")
    private Long imTypeId;

    @Column(name = "ImTypeName")
    private String imTypeName;

    @Column(name = "ImTypeDescription")
    private String imTypeDescription;

    @ManyToMany(cascade = {CascadeType.ALL})
    @JoinTable(name="imageviewer_imtype_variable", 
    joinColumns={@JoinColumn(name="ImTypeId")}, 
    inverseJoinColumns={@JoinColumn(name="VarId")})
    private Set<CRVariable> crvariables = new HashSet<CRVariable>();

CRVariable entity:

@Entity
@Table(name = "imageviewer_crvariable")
public class CRVariable implements Serializable   {

    private static final long serialVersionUID = 1L;

    @Id
    @GeneratedValue
    @Column(name = "VarId")
    private Long varId;

    @Column(name = "VarName")
    private String varName;

    @Column(name = "VarDescription")
    private String varDescription;

    @ManyToMany(mappedBy="crvariables")
    private Set<CRImageType> crimagetypes = new HashSet<CRImageType>();

在我的数据库中,关系由两个表“imageviewer_crimagetype”&amp; “imageviewer_crvariable”和第三个“imageviewer_imtype_variable”因其多对多的关系。

我只想删除表格“imageviewer_imtype_variable”中的关联记录。如何使用HQL查询,因为我无法直接访问“imageviewer_imtype_variable表。

我希望HQL等同于SQL查询,如

delete from imageviewer_imtype_variable where ImTypeId='%%%'

5 个答案:

答案 0 :(得分:2)

这是JPA,而不是Hibernate。如果您在API的上下文中搜索而不是实现,那么您在此处拥有标准化API的事实可以更轻松地找到答案。

这样做的方法(据我记得,我不经常使用多对多关系)是从彼此的集合映射字段中删除相关实体。因此,如果您有EntityA和EntityB,则从EntityA中删除EntityA,从EntityA中删除EntityB。然后应该触发持久性提供程序从连接表中删除记录。

原生查询应该只是IMO的最后手段。

答案 1 :(得分:1)

  • 您可以执行本机SQL查询:

http://docs.jboss.org/hibernate/orm/4.1/manual/en-US/html/ch18.html#querysql-creating

所以在你的情况下,像:

session.createSQLQuery("DELETE FROM imageviewer_imtype_variable").executeUpdate();
  • 您还可以在 CrImageType 实体中指定自定义本机SQL DELETE查询:

http://docs.jboss.org/hibernate/orm/4.1/manual/en-US/html/ch18.html#querysql-cud

答案 2 :(得分:1)

根据我的经验,处理ManyToMany关系是为数不多的情况之一,为了我们的想法,退出ORM整合是最好的选择。特别是,当您使用双向导航时(即当关系和反向关系有用时)。

@Gimby在他的回答中是正确的,事实是,通过复杂的交叉引用,使其工作比执行简单的本机查询要困难得多。

所以:

session.createSQLQuery("DELETE FROM imageviewer_imtype_variable").executeUpdate();

更容易,如果由于交叉引用它仍然不起作用,你甚至可以添加一个:

session.clear();

行。这是另一个ORM整合侵权,但让你从两行中脱离了cesspit ;-)。

答案 3 :(得分:0)

@Gimby的答案是正确的,在多对多的关系中,相互之间删除相关的实例,映射集合会触发从关系映射表中删除。

答案 4 :(得分:0)

在实体类CRVariable中添加:

@PreRemove
private void removeCRVariableFromCRImageType() {
    for (CRImageType crImageType: CRImageType) {
        crImageType.getCrvariables ().remove(this);
    }
}

此方法将覆盖JPA操作PreRemove,以便分离要从set crvariables中删除的CRVariable对象(技术上是表imageviewer_imtype_variable)

希望这能帮到你!