Hibernate在多对多表上进行批量删除 [英] Hibernate batch delete on many-to-many table

查看:107
本文介绍了Hibernate在多对多表上进行批量删除的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

还有另一个多对多的Hibernate问题。我有最简单的多对多映射,如下所示:

  @Entity 
public class Strategy implements Serializable {
@ManyToMany(fetch = FetchType.EAGER)
@JoinTable(name =STRATEGY_TO_GROUP,joinColumns = {@JoinColumn(name =STRATEGY_ID)},inverseJoinColumns = {@JoinColumn(name =STRATEGY_GROUP_ID )})
private Set< StrategyGroup>组;
...
}

关系的反面如下:

  @Entity 
公共类StrategyGroup实现Serializable {

@ManyToMany(fetch = $ name =STRATEGY_ID)}
private设置<策略> strategies = new HashSet< Strategy>();

现在我想要做的是以最简单的方式清空两个表格。

  em.createQuery(从策略组sg中删除)。executeUpdate() ; 
em.createQuery(从策略s中删除)。executeUpdate();

这使我在@joinTable上违反约束条件。另一方面,如果我通过 em.remove(strategyGroup)删除; ti正常工作 - 策略组被删除并且@joinTable被正确更新。



那么我该如何清空餐桌?我需要加载对象并逐个删除它们吗?



感谢您的帮助。

解决方案

首先,你的映射是错误的。关联的一方必须是所有者方,并定义关联的映射。

  @ManyToMany(fetch = FetchType.EAGER,mappedBy = groups)
private Set< Strategy> strategies = new HashSet< Strategy>();

其次,你应该真的避免在一个toMany关联上抓取EAGER,特别是在双方:强制Hibernate以递归方式加载所有关联的实体,并且每次载入一行时都有很好的机会在内存中加载所有的表的行。



现在你问题:

如果要从两个表中删除所有内容,首先需要确保连接表为空,否则其中一个表中的某些行仍然会被连接表的一行所引用,并且会显着失败。要做到这一点,你的情况中最好的选择是在执行你已有的两个HQL查询之前,使用SQL查询来删除连接表中的所有内容。


yet another many-to-many Hibernate questions. I have the simplest possible many-to-many mapping as follows:

@Entity
public class Strategy implements Serializable {
    @ManyToMany(fetch = FetchType.EAGER)
    @JoinTable(name = "STRATEGY_TO_GROUP", joinColumns = {@JoinColumn(name="STRATEGY_ID")}, inverseJoinColumns = {@JoinColumn(name = "STRATEGY_GROUP_ID")})
    private Set<StrategyGroup> groups;
...
}

And the opposite side of the relation as follows:

@Entity
public class StrategyGroup implements Serializable {

    @ManyToMany(fetch = FetchType.EAGER)
    @JoinTable(name = "STRATEGY_TO_GROUP", joinColumns = {@JoinColumn(name="STRATEGY_GROUP_ID")}, inverseJoinColumns = {@JoinColumn(name = "STRATEGY_ID")})
    private Set<Strategy> strategies = new HashSet<Strategy>();

What I want to do now is empty both tables in the easiest possible way. I am trying following (em is my entityManager).

em.createQuery("delete from StrategyGroup sg").executeUpdate();
em.createQuery("delete from Strategy s").executeUpdate();

This gives me constraint violation on the @joinTable. On the other hand if I delete by em.remove(strategyGroup); ti works fine - the strategy group gets deleted and the @joinTable is updated correctly.

So how do I empty the table? Do I need to load the objects and delete them one by one?

Thanks for help.

解决方案

First of all, your mapping is wrong. One side of the association must be the owner side, and define the mapping of the association. The other must be the inserse side, and just use the mappedBy attribute:

@ManyToMany(fetch = FetchType.EAGER, mappedBy = "groups")
private Set<Strategy> strategies = new HashSet<Strategy>();

Second, you should really avoid EAGER fetching on a toMany association, and particularly on both sides: this will force Hibernate to load all the associated entities recursively, and has a good chance to load all the rows of both tables in memory each time you load one row.

Now to your question:

If you want to delete everything from both tables, you first need to make sure that the join table is empty, else some rows in one of the tables will still be referenced by a row of the join table, and it will obviosuly fail. To do that, the best option in your case is to use a SQL query to delete everything from the join table before executing the two HQL queries you already have.

这篇关于Hibernate在多对多表上进行批量删除的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆