双向@ManyToMany不会使用CascadeType.ALL从连接表xx_yy中删除记录

时间:2016-10-14 17:03:42

标签: java hibernate many-to-many entity jpa-2.1

我实施分类系统,其中一个类别通常有几个子类别,一个子类别至少有一个父类别,但肯定会有子类别有多个父类的情况。

这就是我选择ManyToMany方法的原因。

所以,Category

public class Category implements Serializable {

    private static final long serialVersionUID = 1L;
    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    @Basic(optional = false)
    @Column(name = "cat_id", nullable = false)
    private Integer catId;
    ....    
    @ManyToMany(cascade = CascadeType.ALL)
    @JoinTable(
        name = "cats_subcats",
        joinColumns = @JoinColumn(name = "cat_id"),
        inverseJoinColumns = @JoinColumn(name = "subcat_id")
    )
    private Set<Subcategory> subcats;
    ....

Subcategory

public class SubCategory implements Serializable {

    private static final long serialVersionUID = 1L;
    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    @Basic(optional = false)
    @Column(name = "subcat_id", nullable = false)
    private Integer subcatId;
    ....
    @ManyToMany(cascade = CascadeType.ALL, mappedBy = "subcats")
    private Set<Category> cats;
    ....

此设置有效,它创建连接表,插入我的两个虚拟子系统,并在连接表中创建两个连接记录。

然后我继续测试它在不同情况下的表现。

首先,我想从具有三个子类别的现有类别中删除一个子类别。

我的托管bean:

....
@PostConstruct
    public void init() {

    category = new Category();
    category.setName("Programmatically added ctg");
    category.setSlug("programmatically-added-crg");

    Set<Subcategory> subcats = new HashSet<>(2);

    Subcategory subcat = new Subcategory();
    subcat.setName("Subcat one");
    subcats.add(subcat);

    Subcategory subcat2 = new Subcategory();
    subcat2.setName("Subcat to be removed");
    subcats.add(subcat2);

    Subcategory subcat3 = new Subcategory();
    subcat3.setName("The most recent subcat");
    subcats.add(subcat3);

    category.setSubcats(subcats);

    // this initially saves both the cat and the subcats
    ctgService.save(category);
    categories = ctgService.getAll();

    // now I remove one of the three subcats
    category.getSubcats().remove(subcat2);

    // this is a method belonging to my service (EJB)
    ctgService.update(category);

    // upon re-fetching, I can see in my DB that the subcat has not been removed
    categories = ctgService.getAll();
}
....

我通过将(Category实体)@ManyToMany(cascade = CascadeType.ALL)更改为@ManyToMany(cascade = {CascadeType.PERSIST, CascadeType.MERGE})来实现这一目标。

实际上,它会根据需要删除子标记,但是...当我查看我的类别(在这种情况下只有一个)时 - 我可以看到它以某种方式重新插入,因为它现在拥有cat_id 2而不是1

有没有人能够解释我遇到的任何/两个问题?

1 个答案:

答案 0 :(得分:0)

我认为你想要'orpahnremoval',但它不适用于@ManyToMany

How do I delete orphan entities using hibernate and JPA on a many-to-many relationship?