2013-08-23 116 views
5

我需要你的幫助來映射Hibernate中兩個表的關係,使用@ElementCollection註釋中的 。JPA:如何使用@ElementCollection註解?

第一個是父表
表名:
DB色譜柱

KEY1   Char  (first primary key field) 
KEY2   Char  (second primary key field) 
DESCRIPTION Char 
DEPENDENTID BigInt 

第二個是相關表
表名:從屬
DB色譜柱

PARENTID  BigInt (first primary key field) 
CODE   Char  (second primary key field) 
FIELD1  Char 
FIELD2  Char 

我需要使用@EmbeddedId標註來定義兩個表的PK, 所以我創建了兩個類:

@Embeddable 
public class ParentPK implements Serializable 
{ 
    @Column(name="K1") 
    private String iK1; 
    @Column(name="K2") 
    private String iK2; 
    // I omit the constructor, getter, setter, equals, hashcode method 
} 

@Embeddable 
public class DependentPK implements Serializable 
{ 
    @Column(name="PARENTID") 
    private String iParentId; 
    @Column(name="CODE") 
    private String iCode; 
    // I omit the constructor, getter, setter, equals, hashcode method 
} 

,然後我創建了兩個bean:
的相關表中的類。
注意,在這個班,我不希望有任何關係註釋

@Entity 
@Table(name = "DEPENDENT") 
public class DependentBean implements Serializable 
{ 
    @EmbeddedId 
    private DependentPK iDependentPK; 
    @Column(name = "FIELD1") 
    private String iField1; 
    @Column(name = "FIELD2") 
    private String iField2; 
    // I omit the constructor, getter, setter methods 
} 

和類父表

@Entity 
@Table(name = "PARENT") 
public class ParentBean implements Serializable 
{ 
    @EmbeddedId 
    ParentPK iParentPK; 
    @Column(name = "DESCRIPTION") 
    private String iDescription; 
    @Column(name = "DEPENDENTID") 
    private long iDependentId; 
    @ElementCollection 
    @CollectionTable(name="DEPENDENT", joinColumns={@JoinColumn(name="PARENTID", referencedColumnName="DEPENDENTID")}) 
    private Set<DependentBean> iDependentBeans = new HashSet<DependentBean>(); 
    // I omit the constructor, getter, setter methods 
} 

當我嘗試部署我得到了錯誤:

Caused by: org.hibernate.MappingException: Foreign key (FK9619C2A17B05CB2:DEPENDENT [iDependentBeans_PARENTID,iDependentBeans_CODE])) must have same number of columns as the referenced primary key (DEPENDENT [PARENTID,iDependentBeans_PARENTID,iDependentBeans_CODE])

所以我做錯了什麼,但我無法想象是什麼。 任何人都可以幫我嗎?

回答

7

@ElementCollection應該與基本類型或可嵌入類一起使用,而不是用於實體。

DependentBean是一個實體。

嘗試使用一對多映射和修改您的架構

家長模式

KEY1   Char  (PK) 
KEY2   Char  (PK) 
DEPENDENTID BigInt (PK) 
DESCRIPTION Char 

依賴模式

CODE   Char  (PK) 
PARENTID  BigInt (FK) 
KEY1   Char  (FK) 
KEY2   Char  (FK) 
FIELD1  Char 
FIELD2  Char 

一對多映射

ParentPK

@Embeddable 
public class ParentPK { 
    @Column(name = "K1") 
    private String iK1; 
    @Column(name = "K2") 
    private String iK2; 
    @Column(name = "DEPENDENTID") 
    private long iDependentId; 
} 

ParentBean

@Entity 
@Table(name = "PARENT") 
public class ParentBean { 
    @EmbeddedId 
    ParentPK iParentPK; 

    @OneToMany(mappedBy = "parent") 
    List<DependentBean> iDependentBeans; 
} 

DependentBean

@Entity 
@Table(name = "DEPENDENT") 
public class DependentBean { 
    @Id 
    @Column(name = "CODE") 
    private String iCode; 

    @ManyToOne 
    @JoinColumns({ 
     @JoinColumn(name = "PARENTID", referencedColumnName = "iDependentId"), 
     @JoinColumn(name = "K1", referencedColumnName = "iK1"), 
     @JoinColumn(name = "K2", referencedColumnName = "iK2") }) 
    ParentBean parent; 
} 
+0

首先感謝你的答案。 但我已經看到,使用onetomany註釋Hibernate訪問父表時進行連接。 我只有在訪問屬性時才需要訪問依賴表。那麼,有什麼辦法呢? – gpezzini

+0

我想你使用@OneToMany(fetch = FetchType.EAGER),這肯定會按照你的說法進行連接。嘗試使用@OneToMany(fetch = FetchType.LAZY)並確保在關閉會話之前訪問該屬性。否則,你會得到一個LazyInitializationException。 – study

+0

嗨,但可以在我的兩個表** Parent **和** Dependent **之間定義一個OneToMany? 正如您所看到** Parent **表的字段'DEPENDENTID'可能與** Dependent **表的'PARENTID'字段相關聯。 **從屬表**有另一個主鍵字段:'代碼'。 這兩個表具有使用可嵌入類描述的自己的主鍵。 因此,您認爲在這種情況下可以使用@OneToMany註釋嗎? 我已經嘗試了幾種方式沒有成功,我已經嘗試了很多搜索而沒有發現任何東西。 在此先感謝您的時間 – gpezzini