hibernate-annotation CascadeType.PERSIST不起作用的解决方法

有如下两个实体类 , Student和Grade 为多对一关系。

Student.java

 1 @Entity
 2 public class Student {
 3     private Integer id;
 4     private String name;
 5     private Grade grade;
 6     @Id
 7     @GeneratedValue(strategy=GenerationType.AUTO)
 8     public Integer getId() {
 9         return id;
10     }
11     public void setId(Integer id) {
12         this.id = id;
13     }
14     public String getName() {
15         return name;
16     }
17     public void setName(String name) {
18         this.name = name;
19     }
20     @ManyToOne(cascade={CascadeType.PERSIST})
21     @JoinColumn(name="gradeid")
22     public Grade getGrade() {
23         return grade;
24     }
25     public void setGrade(Grade grade) {
26         this.grade = grade;
27     }
28     
29 }

Grade.java

 1 @Entity
 2 public class Grade {
 3 
 4     private Integer id;
 5     private String name;
 6     
 7     @Id
 8     @GeneratedValue(strategy=GenerationType.AUTO)
 9     public Integer getId() {
10         return id;
11     }
12     public void setId(Integer id) {
13         this.id = id;
14     }
15     public String getName() {
16         return name;
17     }
18     public void setName(String name) {
19         this.name = name;
20     }
21 
22 }

可以看到Student类的grade属性已经设置了   @ManyToOne(cascade={CascadeType.PERSIST})

但只save Student对象时依然会报 org.hibernate.TransientObjectException 异常,如下:

public class Init {
    public static void main(String[] args) {
        Session session = HibernateUtil.getSessionFactory().getCurrentSession();
        session.beginTransaction();
        
        Grade g = new Grade();
        g.setName("一班");
        
        Student s = new Student();
        s.setName("张三");
        s.setGrade(g);
        
        session.save(s);
        
        session.getTransaction().commit();
    
    }
}

运行结果:

Exception in thread "main" org.hibernate.TransientObjectException: object references an unsaved transient instance - save the transient instance before flushing: accp.hib.Grade

 

解决办法如下:

方法一:改用persist方法来保存

把session.save(s); 更改为 session.persist(s);

再次保存成功。

Hibernate: select hibernate_sequence.nextval from dual
Hibernate: select hibernate_sequence.nextval from dual
Hibernate: insert into Grade (name, id) values (?, ?)
Hibernate: insert into Student (gradeid, name, id) values (?, ?, ?)

方法二:使用hibernate的自定义的级联,不要使用jpa的

把Student类grade的注解改为hibernate的注解

@ManyToOne(cascade={CascadeType.PERSIST})
@JoinColumn(name="gradeid")

改为:

@ManyToOne
@JoinColumn(name="gradeid")
@Cascade(value={CascadeType.SAVE_UPDATE})

注意,这里的CascadeType和@Cascade都是org.hibernate.annotations包下的,所以把

import javax.persistence.CascadeType;

改为:import org.hibernate.annotations.CascadeType;

并加上:import org.hibernate.annotations.Cascade;

再次保存成功。

posted on 2013-11-07 23:39  喜欢凯的蓝  阅读(1130)  评论(0编辑  收藏  举报