Hibernate:如何在级联中删除?

时间:2011-03-01 20:12:16

标签: java hibernate orm jpa

我有以下课程:

//Product class
public class Product {
@Id
@GeneratedValue
private Long id;
private String name;

//Package Class
public class Package {
@Id
@GeneratedValue
private Long id;

@OneToOne(cascade=CascadeType.ALL)
private Product product;

private int quantity;
private char mode;
private String unity;
private String description;

@OneToOne(cascade=CascadeType.ALL)
private Usuario user;

public class User {
    @Id
    private String email;

我可以插入产品,用户和包:

    //.. (iniatilize product and user before and set in package object) 
    session.save(package);
    session.getTransaction().commit();

那为什么我不能删除用户?

    User user = new User();
    user.setEmail("valter@gmail.com");
    session.delete(user);
    session.getTransaction().commit();

给我这个错误:

  

无法删除或更新父行:   外键约束失败

我的班级出了什么问题?

完整实体用户

@Entity
public class Usuario {
    @Id
    private String email;

    public String getEmail() {
        return email;
    }

    public void setEmail(String email) {
        this.email = email;
    }

}

@Entity
public class Package{
    @Id
    @GeneratedValue
    private Long id;

    @OneToOne(cascade=CascadeType.ALL)
    private Product product;

    private int quantity;
    private char mode;
    private String unity;
    private String description;

    @OneToOne(cascade=CascadeType.ALL)
    private User user;


@Entity
public class Product {
    @Id
    @GeneratedValue
    private Long id;
    private String name;

这是系统中包含的所有实体。

@Bozho基于你所说的,它应该是这样的吗?

@Entity
public class User{
    @Id
    private String email;

    @OneToOne(cascade=CascadeType.ALL)
    private List<Package> packages;

我正在尝试执行此方法:

    private static void deleteUser() {
    Session session = new HibernateUtil().getSession();
    session.beginTransaction();

    try{

        User usuario = (Usuario) session.load(Usuario.class, "valter@gmail.com");
        session.delete(usuario);
        session.getTransaction().commit();


    }catch(HibernateException he){
        session.getTransaction().rollback();
    }finally{
        session.close();
    }
}

3 个答案:

答案 0 :(得分:2)

您似乎正在创建一个分离的实体并尝试删除它,而不是从数据库中获取一个完整的实体。在这种情况下,即使您定义了级联,它们也无法工作,因为并未填充User实体的关系。

如果电子邮件是主键,那么您应该执行以下操作:

User user = session.load(User.class, "foo@bar.com");
session.delete(user)

即使这样,如果任何其他实体引用User,它将在逻辑上失败 - 只需查看数据库约束。您有多种方法可以解决此问题:

  • 在您的用户中映射List<Package>,从而使关系成双向。因此,您也可以在User侧设置级联
  • 在删除用户之前(通过查询)查找属于他的所有包,并删除它们。
  • 如果包没有任何其他级联,请使用HQL查询:DELETE FROM Package WHERE user=:user"

答案 1 :(得分:1)

你应该添加orphanRemoval = true。

@OneToOne(cascade = CascadeType.ALL,orphanRemoval = true) 私人Usuario用户;

答案 2 :(得分:0)

尝试更新您的包类,例如

private static void deleteUser(Package package) {
Session session = new HibernateUtil().getSession();
session.beginTransaction();

try{

    User usuario = (Usuario) session.load(Usuario.class, "valter@gmail.com");
    package.setUser(null);
    session.merge(package);
    session.delete(usuario);
    session.getTransaction().commit();


}catch(HibernateException he){
    session.getTransaction().rollback();
}finally{
    session.close();
}}