JPA中@JoinTable和@JoinColumn註解的使用
預設情況下,JPA 持續性提供程式在對映多對多關聯(或在單向的一對多關聯中)的擁有方上的實體關聯時使用一個連線表。連線表名稱及其列名均在預設情況下指定,且 JPA 持續性提供程式假設:在關係的擁有方上的實體主表中,每個主鍵列有一個連線列。
通過表關聯的方式來對映一對多或者多對多的關係時,要使用@JoinTable這個標記。該標記的定義如下所示。
@Target({METHOD, FIELD})
public @interface JoinTable {
String name() default "";
String catalog() default "";
String schema() default "";
JoinColumn[] joinColumns() default {};
JoinColumn[] inverseJoinColumns() default {};
UniqueConstraint[] uniqueConstraints default {};
}
在使用此@JoinTable標記時,需要注意以下幾個問題。
l 該標記與@Table註釋類似,用於標註用於關聯的表。可以標註在方法或者屬性上,屬性catalog、schema和uniqueConstraint與@Table註釋中的屬性意義類似,請讀者參閱@Table註釋說明的部分。
l name屬性為連線兩個表的表名稱。若不指定,則使用預設的表名稱如下所示。
“表名1”+“_”+“表名2”。
例如以上的程式碼中,如果不指定name的名稱,預設的儲存關係的名稱如下所示。
“customer_address”。
l joinColumns屬性表示,在儲存關係中的表中,所儲存關聯關係的外來鍵的欄位。並配合@JoinColumn標記使用。
例如以下的對映配置,表示欄位customer_id為外來鍵關聯到customer表中的id欄位。
joinColumns={
@JoinColumn(name="customer_id",referencedColumnName="id")
}
l inverseJoinColumns屬性與joinColumns屬性類似,它儲存的是儲存關係的另一個外來鍵欄位。
例如以下的對映配置,表示欄位address_id為外來鍵關聯到address表中的id欄位。
inverseJoinColumns={
@JoinColumn(name="address_id",referencedColumnName="id")
}
提示:@JoinTable不僅能夠定義一對多的關聯,也可以定義多對多表的關聯
@JoinColumn
預設情況下,在實體關聯中,JPA 持續性提供程式使用一個基於現有名稱(如欄位或屬性名稱)的資料庫模式,以便它可以自動確定要使用的單個連線列(包含外來鍵的列)。
在以下條件下使用 @JoinColumn
@JoinColumn 屬性
屬性 | 必需 | 說明 |
---|---|---|
|
|
預設值:空 JPA 使用最少量 SQL 建立一個數據庫表列。
如果需要使用更多指定選項建立列,請將 |
|
|
預設值: 預設情況下,JPA 持續性提供程式假設它可以插入到所有表列中。
如果該列為只讀,請將 |
|
|
預設值:如果使用一個連線列,則 JPA 持續性提供程式假設外來鍵列的名稱是以下名稱的連線:
如果實體中沒有這樣的引用關係屬性或欄位(請參閱 @JoinTable),則連線列名稱格式化為以下名稱的連線:實體名稱 +“_”+ 被引用的主鍵列的名稱。 這是外來鍵列的名稱。如果連線針對“一對一”或“多對一”實體關係,則該列位於源實體的表中。如果連線針對“多對多”實體關係,則該列位於連線表(請參閱 @JoinTable)中。
如果連線列名難於處理、是一個保留字、與預先存在的資料模型不相容或作為資料庫中的列名無效,請將 |
|
|
預設值: 預設情況下,JPA 持續性提供程式假設允許所有列包含空值。
如果不允許該列包含空值,請將 |
|
|
預設值:如果使用一個連線列,則 JPA 持續性提供程式假設在實體關係中,被引用的列名是被引用的主鍵列的名稱。 如果在連線表(請參閱 @JoinTable)中使用,則被引用的鍵列位於擁有實體(如果連線是反向連線定義的一部分,則為反向實體)的實體表中。
要指定其他列名,請將 |
|
|
預設值:JPA 持續性提供程式假設實體的所有持久欄位儲存到一個名稱為實體類名稱的資料庫表中(請參閱 @Table)。
如果該列與輔助表關聯(請參閱 @SecondaryTable),請將 |
|
|
預設值: 預設情況下,JPA 持續性提供程式假設允許所有列包含重複值。
如果不允許該列包含重複值,請將 |
|
|
預設值: 預設情況下,JPA 持續性提供程式假設它可以更新所有表列。
如果該列為只讀,則將 |
下例顯示瞭如何使用此批註使 JPA 將資料庫表 Employee
列 ADDR_ID
用作連線列。
@Entity public class Employee implements Serializable { ... @ManyToOne @JoinColumn(name="ADDR_ID") public Address getAddress() { return address; } }