JPA / Hibernate即使不应该继续保持级联

时间:2011-11-03 09:04:33

标签: java hibernate jpa persistence

我有这两个实体:

@javax.persistence.Entity
public class Book {
    @javax.persistence.EmbeddedId
    private BookPK id;

    private String title;

    @javax.persistence.ManyToOne(fetch = javax.persistence.FetchType.LAZY)
    @javax.persistence.JoinColumns({ 
            @javax.persistence.JoinColumn(name = "LNGCOD", referencedColumnName = "LNGCOD"),
            @javax.persistence.JoinColumn(name = "LIBCOD", referencedColumnName = "LIBCOD") })
    private Language language;
}

@javax.persistence.Entity
public class Language {
    @javax.persistence.EmbeddedId
    private LanguagePK id;

    private String name;
}

用组合PK:

@Embeddable
public class BookPK implements Serializable {
    private Integer bookcod;
    private Integer libcod;
}

@Embeddable
public class LanguagePK implements Serializable {
    private Integer lngcod;
    private Integer libcod;
}

如果我尝试创建一个新书并坚持下去,我会得到一个异常,告诉我在insert语句中找到了两次libcod(“Column'libcod'指定了两次”)。但是在定义JoinColumn时我不能使用“insertable = false”(“不允许在属性中混合可插入和不可插入的列”)。

有没有办法定义这些对象+关系,所以这些列是由Hibernate自动管理的?

2 个答案:

答案 0 :(得分:2)

Hibernate和JPA会自动对持久化实体附加到会话时所做的所有修改。这就是ORM的重点:你加载一个持久对象,修改它,并且在事务提交时自动保持新状态,而不需要调用persist,merge,save或任何其他方法。

请注意,在持久性实体上调用persist(其级联副作用除外)是没有意义的。 persist是一个暂时的实体(即一个新的实体,不在数据库中,没有生成的ID)持久化。

答案 1 :(得分:0)

你只能为libcod提供一个mutator。也许你应该做的是将libcod getter保留在BookPK类中,在Language类中,使用带有ref的joincolumn引用返回libcod。它适用于单个嵌入式PK类,但对于多个PK类,您可能不得不玩。

所以,在你的语言课上,你会有这个。

    @javax.persistence.Entity public class Language {

    private LanguagePK id;
    private Integer    libcod;

    @javax.persistence.EmbeddedId @AttributeOverrides({
        @AttributeOverride(name = "lngcod", column = @Column(name = "LNGCOD", nullable = false)),
        @AttributeOverride(name = "libcod", column = @Column(name = "LIBCOD", nullable = false)) })
    public LanguagePK getId() {
            return this.id;
    }
     public void setId(LanguagePK id) {
          this.id = id;
    }    


    @ManyToOne(fetch = FetchType.LAZY)

       @JoinColumn(name = "LIBCOD", insertable = false , updatable = false)
         public Integer getLibcod() {
       return this.libcod;
         }