1. 程式人生 > >《Hibernate快速開始》Query /HQL and JPQL (上)

《Hibernate快速開始》Query /HQL and JPQL (上)


@NamedQueries({//將多個命名查詢附加到相同的實體類需要將它們包裝在@NamedQueries註釋中
@NamedQuery(定義了一個名稱為“get_person_by_name”的查詢
name = "get_person_by_name",
//查詢語句
query = "select p from Person p where name = :name"
)
,
@NamedQuery(
name = "get_read_only_person_by_name",
query = "select p from Person p where name = :name",
hints = {
@QueryHint(//@QueryHint 批註指定供應商特定的 JPA 查詢擴充套件,提高查詢效能,利用Hibernate的 JPA 持續性提供程式實現中的特定特性
name = "org.hibernate.readOnly",
value = "true"
)
}
)
})
@NamedStoredProcedureQueries(//使用@NamedStoredProcedureQueries註解來呼叫儲存過程
@NamedStoredProcedureQuery(//使用@NamedStoredProcedureQuery註解並繫結到一個JPA表
name = "sp_person_phones",//JPA中的儲存過程的名字
procedureName = "sp_person_phones",//儲存過程的名字
parameters = {
@StoredProcedureParameter(//使用註解@StoredProcedureParameter來定義儲存過程使用的IN/OUT引數
name = "personId",
type = Long.class,
mode = ParameterMode.IN
),
@StoredProcedureParameter(
name = "personPhones",
type = Class.class,
mode = ParameterMode.REF_CURSOR
)
}
)
)
@Entity//@Entity註解定義一個實體
public class Person {
@Id//@Id宣告此欄位為主鍵
@GeneratedValue//為一個實體生成一個唯一標識的主鍵(JPA要求每一個實體Entity,必須有且只有一個主鍵),@GeneratedValue提供了主鍵的生成策略
private String name;private String nickName;private String address;@Temporal(TemporalType.TIMESTAMP )//@Temporal註解Date格式的欄位,獲得”HH:MM:SS”日期格式[引申]TemporalType.TIME也會得到形如’HH:MM:SS’ 格式的日期,TemporalType.DATE 會得到形如’yyyy-MM-dd’ 格式的日期
private Date createdOn;@OneToMany(mappedBy = “person”, cascade = CascadeType.ALL)//@OneToMany用來配置一對多關聯對映 在JPA中,在@OneToMany里加入mappedBy屬性可以避免生成一張中間表。cascade:設定級聯操作型別,CascadeType.ALL包含所有持久化方法
@OrderColumn(name = “order_id”)//@OrderColumn註解根據指定的列進行排序
private List phones = new ArrayList<>();

@ElementCollection//JPA通過@ElementCollection註解集合對映,可以自動檢測元素型別
@MapKeyEnumerated(EnumType.STRING)//指定基本型別為列舉型別的對映鍵的列舉型別,MapKeyEnumerated註釋可以應用於一個元素集合或型別的關係
private Map<AddressType, String> addresses = new HashMap<>();

@Version//JPA通過在實體類中使用@Version註解來發現資料庫記錄的併發操作,如果資料被修改,JPA會將這個欄位自增,如果還有別的實體也在操作,它會丟擲一個嘗試提交的事務異常
private int version;

//Getters and setters are omitted for brevity

}

public enum AddressType {
HOME,
OFFICE
}

@Entity
public class Partner {

@Id
@GeneratedValue
private Long id;

private String name;

@Version
private int version;

//Getters and setters are omitted for brevity

}

@Entity
public class Phone {

@Id
private Long id;

@ManyToOne(fetch = FetchType.LAZY)//@ManyToOne用來配置多對一關聯對映,表示在多的那一方通過延遲載入的方式載入物件(預設是非延遲載入)
private Person person;

@Column(name = “phone_number”)//@Column註解來標識實體類中屬性與資料表中欄位的對應關係
private String number;

@Enumerated(EnumType.STRING)
@Column(name = “phone_type”)
private PhoneType type;

@OneToMany(mappedBy = “phone”, cascade = CascadeType.ALL, orphanRemoval = true)// orphanRemoval 設定級聯刪除 , true代表自動刪除
private List calls = new ArrayList<>( );

@OneToMany(mappedBy = “phone”)
@MapKey(name = “timestamp”)//@MapKey指定了對映,持久化timestamp或者timestamp的值
@MapKeyTemporal(TemporalType.TIMESTAMP )//@MapKeyTemporal應用於java.util.map型別的元素集合或關係
private Map<Date, Call> callHistory = new HashMap<>();

@ElementCollection
private List repairTimestamps = new ArrayList<>( );

//Getters and setters are omitted for brevity

}

public enum PhoneType {
LAND_LINE,
MOBILE;
}

@Entity
@Table(name = “phone_call”)@Table用於指明資料庫的表名,若不指定則以實體類名稱作為表名
public class Call {

@Id
@GeneratedValue
private Long id;

@ManyToOne
private Phone phone;

@Column(name = “call_timestamp”)
private Date timestamp;

private int duration;

//Getters and setters are omitted for brevity

}

@Entity
@Inheritance(strategy = InheritanceType.JOINED)//@Inheritance定義繼承的策略,有SINGLE_TABLE、TABLE_PER_CLASS 和 JOINED 三種,JOINED 是將父類、子類分別存放在不同的表中,並且建立相應的外來鍵,以確定相互之間的關係
public class Payment {

@Id
@GeneratedValue
private Long id;

private BigDecimal amount;

private boolean completed;

@ManyToOne
private Person person;

//Getters and setters are omitted for brevity

}

@Entity
public class CreditCardPayment extends Payment {
}

@Entity
public class WireTransferPayment extends Payment {
}