The next example shows the definition of a sequence generator in a class scope:
1 2 3 4 5 6 7 8 9 10
@Entity @javax.persistence.SequenceGenerator( name="SEQ_STORE", sequenceName="my_sequence" ) public class Store implements Serializable { private Long id; @Id @GeneratedValue(strategy=GenerationType.SEQUENCE, generator="SEQ_STORE") public Long getId() { return id; } }
@Entity @IdClass(FootballerPk.class) public class Footballer { //part of the id key @Id public String getFirstname() { return firstname; } public void setFirstname(String firstname) { this.firstname = firstname; } //part of the id key @Id public String getLastname() { return lastname; } public void setLastname(String lastname) { this.lastname = lastname; } public String getClub() { return club; } public void setClub(String club) { this.club = club; } //appropriate equals() and hashCode() implementation } @Embeddable public class FootballerPk implements Serializable { //same name and type as in Footballer public String getFirstname() { return firstname; } public void setFirstname(String firstname) { this.firstname = firstname; } //same name and type as in Footballer public String getLastname() { return lastname; } public void setLastname(String lastname) { this.lastname = lastname; } //appropriate equals() and hashCode() implementation } @Entity @AssociationOverride( name="id.channel", joinColumns = @JoinColumn(name="chan_id") ) public class TvMagazin { @EmbeddedId public TvMagazinPk id; @Temporal(TemporalType.TIME) Date time; }
@Embeddable public class TvMagazinPk implements Serializable { @ManyToOne public Channel channel; public String name; @ManyToOne public Presenter presenter; }
映射继承关系
EJB支持3种类型的继承。
Table per Class Strategy: theelement in Hibernate 每个类一张表
Single Table per Class Hierarchy Strategy: theelement in Hibernate 每个类层次结构一张表
Joined Subclass Strategy: theelement in Hibernate 连接的子类策略 @Inheritance 注解来定义所选的之类策略。
每个类一张表
1 2 3
@Entity @Inheritance(strategy = InheritanceType.TABLE_PER_CLASS) public class Flight implements Serializable {
有缺点,如多态查询或关联。Hibernate 使用 SQL Union 查询来实现这种策略。 这种策略支持双向的一对多关联,但不支持 IDENTIFY 生成器策略,因为ID必须在多个表间共享。一旦使用就不能使用AUTO和IDENTIFY生成器。
每个类层次结构一张表
1 2 3 4 5 6 7 8 9 10 11 12
@Entity @Inheritance(strategy=InheritanceType.SINGLE_TABLE) @DiscriminatorColumn( name="planetype", discriminatorType=DiscriminatorType.STRING ) @DiscriminatorValue("Plane") public class Plane { ... }
@Entity @DiscriminatorValue("A320") public class A320 extends Plane { ... }
@MappedSuperclass public class BaseEntity { @Basic @Temporal(TemporalType.TIMESTAMP) public Date getLastUpdate() { ... } public String getLastUpdater() { ... } ... }
@Entity class Order extends BaseEntity { @Id public Integer getId() { ... } ... }
继承父类的一些属性,但不用父类作为映射实体,这时候需要 @MappedSuperclass 注解。 上述实体映射到数据库中的时候对应 Order 实体Bean, 其具有 id, lastUpdate, lastUpdater 三个属性。如果没有@MappedSuperclass 注解,则父类中属性忽略,这是 Order 实体 Bean 只有 id 一个属性。
映射实体Bean的关联关系
一对一
使用 @OneToOne 注解可以建立实体Bean之间的一对一关系。一对一关系有3种情况。
关联的实体都共享同样的主键。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16
@Entity public class Body { @Id public Long getId() { return id; } @OneToOne(cascade = CascadeType.ALL) @PrimaryKeyJoinColumn public Heart getHeart() { return heart; } ... } @Entity public class Heart { @Id public Long getId() { ...} }
通过@PrimaryKeyJoinColumn 注解定义了一对一的关联关系。
其中一个实体通过外键关联到另一个实体的主键。注:一对一,则外键必须为唯一约束。
1 2 3 4 5 6 7 8 9 10 11 12 13 14
@Entity public class Customer implements Serializable { @OneToOne(cascade = CascadeType.ALL) @JoinColumn(name="passport_fk") public Passport getPassport() { ... }
@Entity public class Passport implements Serializable { @OneToOne(mappedBy = "passport") public Customer getOwner() { ... }
@Entity() public class Flight implements Serializable { @ManyToOne(cascade= ,targetEntity= CompanyImpl.class) @JoinColumn(name="COMP_ID") public Company getCompany() { return company; } ... }
CascadeType.PERSIST: cascades the persist (create) operation to associated entities persist() is called or if the entity is managed 如果一个实体是受管状态,或者当 persist() 函数被调用时,触发级联创建(create)操作。
CascadeType.MERGE: cascades the merge operation to associated entities if merge() is called or if the entity is managed 如果一个实体是受管状态,或者当 merge() 函数被调用时,触发级联合并(merge)操作。
CascadeType.REMOVE: cascades the remove operation to associated entities if delete() is called 当 delete() 函数被调用时,触发级联删除(remove)操作。
CascadeType.REFRESH: cascades the refresh operation to associated entities if refresh() is called 当 refresh() 函数被调用时,出发级联更新(refresh)操作。
<entity-mappings> <named-query name="plane.getAll"> <query>select p from Plane p</query> </named-query> ... </entity-mappings> ... @Entity @NamedQuery(name="night.moreRecentThan", query="select n from Night n where n.date >= :date") public class Night { ... } public class MyDao { doStuff() { Query q = s.getNamedQuery("night.moreRecentThan"); q.setDate( "date", aMonthAgo ); List results = q.list(); ... } ... }
可以通过定义 QueryHint 数组的 hints 属性为查询提供一些 hint 信息。下图是一些 Hibernate hints:
mutable: whether this entity is mutable or not 此实体是否可变
dynamicInsert: allow dynamic SQL for inserts 用动态SQL新增
dynamicUpdate: allow dynamic SQL for updates 用动态SQL更新
selectBeforeUpdate: Specifies that Hibernate should never perform an SQL UPDATE unless it is certain that an object is actually modified.指明Hibernate从不运行SQL Update,除非能确定对象已经被修改
polymorphism: whether the entity polymorphism is of PolymorphismType.IMPLICIT (default) or PolymorphismType.EXPLICIT 指出实体多态是 PolymorphismType.IMPLICIT(默认)还是PolymorphismType.EXPLICIT
optimisticLock: optimistic locking strategy (OptimisticLockType.VERSION, OptimisticLockType.NONE, OptimisticLockType.DIRTY or OptimisticLockType.ALL) 乐观锁策略