Hibernate 多对多关系-休眠

Hibernate 多对多关系-休眠,hibernate,many-to-many,cascade,Hibernate,Many To Many,Cascade,我正在使用hibernate-jpa-2.0-api 1.0.0.Final和hibernate 3.5.5-Final 我有用户实体和角色实体,每个实体之间都有多对多关系(双向)。我有以下要求: 1-如果调用了deleteRole(role)方法,并且此角色有用户,则hibernate应引发异常,否则可以成功删除该角色。 2-如果调用deleteUser(用户)方法,则可以成功删除用户,并自动从关系表中删除相关记录,但不应删除其角色。 3-futhermore;如果我创建新角色并将一些用户添加

我正在使用hibernate-jpa-2.0-api 1.0.0.Final和hibernate 3.5.5-Final

我有用户实体和角色实体,每个实体之间都有多对多关系(双向)。我有以下要求:

1-如果调用了deleteRole(role)方法,并且此角色有用户,则hibernate应引发异常,否则可以成功删除该角色。
2-如果调用deleteUser(用户)方法,则可以成功删除用户,并自动从关系表中删除相关记录,但不应删除其角色。
3-futhermore;如果我创建新角色并将一些用户添加到其集合中并最终持久化该角色,则应该持久化其用户,而不需要额外的持久化操作

假设角色是Test1用户是Test2。实体:

Test1(角色)

import java.util.HashSet;
import java.util.Set;

import javax.persistence.CascadeType;
import javax.persistence.Entity;
import javax.persistence.JoinColumn;
import javax.persistence.JoinTable;
import javax.persistence.ManyToMany;

import com.ttnet.model.BaseModel;

@Entity
public class Test1 extends BaseModel {

    @ManyToMany(targetEntity = Test2.class, cascade = { CascadeType.ALL })
    @JoinTable(name = "test1_test2", joinColumns = { @JoinColumn(name = "id1", nullable = false, updatable = false) }, inverseJoinColumns = { @JoinColumn(name = "id2", nullable = false, updatable = false) })
    private Set<Test2> test2s = new HashSet<Test2>(0);

    public Set<Test2> getTest2s() {
        return test2s;
    }

    public void setTest2s(Set<Test2> test2s) {
        this.test2s = test2s;
    }
}  
import java.util.HashSet;
import java.util.Set;

import javax.persistence.Entity;
import javax.persistence.ManyToMany;

import com.ttnet.model.BaseModel;

@Entity
public class Test2 extends BaseModel {

    @ManyToMany(targetEntity=Test1.class, mappedBy = "test2s")
    private Set<Test1> test1s = new HashSet<Test1>(0);

    public Set<Test1> getTest1s() {
        return test1s;
    }

    public void setTest1s(Set<Test1> test1s) {
        this.test1s = test1s;
    }
}
import java.util.HashSet;
导入java.util.Set;
导入javax.persistence.CascadeType;
导入javax.persistence.Entity;
导入javax.persistence.JoinColumn;
导入javax.persistence.JoinTable;
导入javax.persistence.ManyToMany;
导入com.ttnet.model.BaseModel;
@实体
公共类Test1扩展了BaseModel{
@ManyToMany(targetEntity=Test2.class,cascade={CascadeType.ALL})
@JoinTable(name=“test1_test2”,joinColumns={@JoinColumn(name=“id1”,nullable=false,updateable=false)},inverseJoinColumns={@JoinColumn(name=“id2”,nullable=false,updateable=false)})
私有集test2s=新哈希集(0);
公共集getTest2s(){
返回test2s;
}
公共无效设置测试2(设置测试2){
这个.test2s=test2s;
}
}  
Test2(用户)

import java.util.HashSet;
import java.util.Set;

import javax.persistence.CascadeType;
import javax.persistence.Entity;
import javax.persistence.JoinColumn;
import javax.persistence.JoinTable;
import javax.persistence.ManyToMany;

import com.ttnet.model.BaseModel;

@Entity
public class Test1 extends BaseModel {

    @ManyToMany(targetEntity = Test2.class, cascade = { CascadeType.ALL })
    @JoinTable(name = "test1_test2", joinColumns = { @JoinColumn(name = "id1", nullable = false, updatable = false) }, inverseJoinColumns = { @JoinColumn(name = "id2", nullable = false, updatable = false) })
    private Set<Test2> test2s = new HashSet<Test2>(0);

    public Set<Test2> getTest2s() {
        return test2s;
    }

    public void setTest2s(Set<Test2> test2s) {
        this.test2s = test2s;
    }
}  
import java.util.HashSet;
import java.util.Set;

import javax.persistence.Entity;
import javax.persistence.ManyToMany;

import com.ttnet.model.BaseModel;

@Entity
public class Test2 extends BaseModel {

    @ManyToMany(targetEntity=Test1.class, mappedBy = "test2s")
    private Set<Test1> test1s = new HashSet<Test1>(0);

    public Set<Test1> getTest1s() {
        return test1s;
    }

    public void setTest1s(Set<Test1> test1s) {
        this.test1s = test1s;
    }
}
import java.util.HashSet;
导入java.util.Set;
导入javax.persistence.Entity;
导入javax.persistence.ManyToMany;
导入com.ttnet.model.BaseModel;
@实体
公共类Test2扩展了BaseModel{
@ManyToMany(targetEntity=Test1.class,mappedBy=“test2s”)
私有集test1s=新哈希集(0);
公共集getTest1s(){
返回test1s;
}
公共void setst1s(Set test1s){
this.test1s=test1s;
}
}
测试代码

    Test1Bo test1Bo = (Test1Bo) context.getBean("test1Bo");
    Test2Bo test2Bo = (Test2Bo) context.getBean("test2Bo");

    Test1 t1 = new Test1();
    Test2 t21 = new Test2();
    Test2 t22 = new Test2();

    Set<Test2> t2Set = t1.getTest2s();
    t2Set.add(t21);
    t2Set.add(t22);


    test1Bo.addTest1(t1);  
Test1Bo Test1Bo=(Test1Bo)context.getBean(“Test1Bo”);
Test2Bo Test2Bo=(Test2Bo)context.getBean(“Test2Bo”);
Test1 t1=新的Test1();
Test2 t21=新的Test2();
Test2 t22=新的Test2();
Set t2Set=t1.getTest2s();
t2Set.add(t21);
t2Set.add(t22);
test1Bo.addTest1(t1);

此代码成功地将预期的entires添加到所有3个表中。然而,起初我只尝试了Cascade.PERSIST和Cascade.MERGE,它给出了未保存的对象异常。然后我尝试了所有的方法,并取得了成功。有趣的是,我添加了所有javax级联操作,我的意思是单独添加,但没有成功抛出相同的异常(未保存的obj…)。现在的问题是,每当我删除t1时,它也会删除t21和t22,这违反了req.1

如果(!t1.getTest2s().size>0)抛出新异常(),则可以
否?当然是,但我想知道是否有一种hibernate可注释的方法来解决这个问题。另外,还有一个问题,你应该把你的建议放在bo层还是dao层?我的意思是,考虑到基于角色的访问控制设计,这个限制与业务需求或数据建模有关吗?我不认为hibernate有内置的东西,因为它闻起来很像业务规则。我会将支票并入业务层。它还可能更改为“如果删除了角色,请将其所有用户移动到默认角色”