Аннотации JPA — аннотации Hibernate
Аннотации JPA используются для сопоставления объектов Java с таблицами базы данных, столбцами и т. д. Hibernate является наиболее популярной реализацией спецификации JPA и предоставляет некоторые дополнительные аннотации. Сегодня мы рассмотрим аннотации JPA, а также аннотации Hibernate с краткими фрагментами кода.
Аннотации JPA — аннотации Hibernate
<dependency>
<groupId>org.hibernate.javax.persistence</groupId>
<artifactId>hibernate-jpa-2.1-api</artifactId>
<version>1.0.0.Final</version>
</dependency>
Аннотации JPA для сопоставления объекта Java с таблицей базы данных
Давайте посмотрим на некоторые важные аннотации JPA. Обратите внимание, что эти аннотации присутствуют в пакете javax.persistence
.
-
javax.persistence.Entity
: Specifies that the class is an entity. This annotation can be applied on Class, Interface of Enums.import javax.persistence.Entity; @Entity public class Employee implements Serializable { }
-
@Table
: It specifies the table in the database with which this entity is mapped. In the example below the data will be stores in the “employee” table. Name attribute of @Table annotation is used to specify the table name.import javax.persistence.Entity; import javax.persistence.Table; @Entity @Table(name = "employee") public class Employee implements Serializable { }
-
@Column
: Specify the column mapping using @Column annotation. Name attribute of this annotation is used for specifying the table’s column name.import javax.persistence.Column; import javax.persistence.Entity; import javax.persistence.Table; @Entity @Table(name = "employee") public class Employee implements Serializable { @Column(name = "employee_name") private String employeeName; }
-
@Id
: This annotation specifies the primary key of the entity.import javax.persistence.*; @Entity @Table(name = "employee") public class Employee implements Serializable { @Id @Column(name = "id") private int id; }
-
@GeneratedValue
: This annotation specifies the generation strategies for the values of primary keys.import javax.persistence.*; @Entity @Table(name = "employee") public class Employee implements Serializable { @Id @Column(name = "id") @GeneratedValue(strategy=SEQUENCE, generator="ID_SEQ") private int id; }
-
@Version
: We can control versioning or concurrency using this annotation.import javax.persistence.*; @Entity @Table(name = "employee") public class Employee implements Serializable { @Version @Column(name = "version") private Date version; }
-
@OrderBy
: Sort your data using @OrderBy annotation. In example below, it will sort all employees_address by their id in ascending order.@OrderBy("id asc") private Set employee_address;
-
@Transient
: Every non static and non-transient property of an entity is considered persistent, unless you annotate it as @Transient.@Transient Private int employeePhone;
-
@Lob
: Large objects are declared with @Lob.@Lob public String getEmployeeAddress() { return employeeAddress; }
Приведенный выше набор аннотаций чаще всего используется для определения объекта.
Аннотации Hibernate для отображения между таблицами
У нас есть еще один набор аннотаций, которые используются для указания сопоставления ассоциаций между различными таблицами и сущностями. Мы возьмем пример, рассматривая нижеприведенный сценарий.
- Таблицы employee и employeeDetail связаны друг с другом и имеют один и тот же первичный ключ.
- Таблицы «связь» и «сведения о связи» связаны внешним ключом. Это также связь один к одному.
- Таблицы «связь» и «сотрудник» связаны с помощью внешнего ключа в ассоциации «многие к одному», при этом владельцем является связь.
- Таблицы employee и employeeStatus связаны через внешний ключ в ассоциации многие к одному, где сотрудник является владельцем.
@OneToOne
Сущности Employee и EmployeeDetail имеют один и тот же первичный ключ, и мы можем связать их с помощью @GeneratedValue. Значение идентификатора Employee будет использоваться для идентификатора EmployeeDetail.
@Entity
@Table(name = "employee")
public class Employee implements Serializable {
@Id
@Column(name = "id")
@GeneratedValue
private int id;
@OneToOne(cascade = CascadeType.MERGE)
@PrimaryKeyJoinColumn
private EmployeeDetail employeeDetail;
}
@Entity
@Table(name = "employeeDetail")
public class EmployeeDetail implements Serializable {
@Id
@Column(name = "id")
private int id;
}
Обратите внимание:
- @PrimaryKeyJoinColumn следует использовать для связанных сущностей, использующих один и тот же первичный ключ.
- @OneToOne должен иметь атрибут mappedBy, если внешний ключ принадлежит одному из объектов.
Communication и CommunicationDetail связаны через внешний ключ, поэтому @MapsId используется для того же.
@Entity
@Table(name = "communicationDetail")
public class CommunicationDetail implements Serializable {
@Id
@Column(name = "id")
@GeneratedValue
private int id;
@OneToOne
@MapsId
@JoinColumn(name = "communicationId")
private Communication communication;
}
@Entity
@Table(name = "communication")
public class Communication implements Serializable {
@Id
@Column(name = "ID")
@GeneratedValue
private Integer id;
@OneToOne(mappedBy = "communication", cascade = CascadeType.ALL)
private CommunicationDetail communicationDetail;
}
@ManyToOne
Многие сотрудники могут иметь один и тот же статус. Таким образом, отношение «сотрудник к статусу сотрудника» является отношением «многие к одному». Для этого можно использовать аннотацию @ManyToOne.
@Entity
@Table(name = "employee")
public class Employee implements Serializable {
@ManyToOne
@JoinColumn(name = "statusId")
private EmployeeStatus status;
}
@OneToMany
Сотрудник для общения будет отношением один ко многим. Владельцем этого отношения является Communication, поэтому мы будем использовать атрибут mappedBy в Employee, чтобы сделать его двунаправленным.
@Entity
@Table(name = "employee")
public class Employee implements Serializable {
@OneToMany(mappedBy = "employee", fetch = FetchType.EAGER)
@OrderBy("firstName asc")
private Set communications;
}
@PrimaryKeyJoinColumn
Эта аннотация используется для связывания объектов, использующих один и тот же первичный ключ.
@Entity
@Table(name = "employee")
public class Employee implements Serializable {
@Id
@Column(name = "id")
@GeneratedValue
private int id;
@OneToOne(cascade = CascadeType.MERGE)
@PrimaryKeyJoinColumn
private EmployeeDetail employeeDetail;
}
@JoinColumn
@JoinColumn аннотация используется для ассоциаций «один к одному» или «многие к одному», когда внешний ключ удерживается одним из объектов.
@ManyToOne
@JoinColumn(name = "statusId")
private EmployeeStatus status;
@JoinTable
: аннотация @MapsId.
@OneToOne
@MapsId
@JoinColumn(name = "communicationId")
private Communication communication;
Аннотации Hibernate для сопоставления наследования
Теперь давайте попробуем понять аннотацию сопоставления наследования в Hibernate. Hibernate поддерживает три основные стратегии сопоставления наследования:
- таблица для каждой иерархии классов
- таблица для каждого подкласса
- таблица для каждого конкретного класса
мы рассмотрим пример для каждого типа.
-
Table per class hierarchy - single table per Class Hierarchy Strategy.
@Entity @Inheritance(strategy=InheritanceType.SINGLE_TABLE) @DiscriminatorColumn(name="cartype", discriminatorType=DiscriminatorType.STRING ) @DiscriminatorValue("Car") public class Car { } @Entity @DiscriminatorValue("BMW") public class BMW extends Car { }
-
Table per class/subclass - joined subclass Strategy.
@Entity @Inheritance(strategy=InheritanceType.JOINED) public class Ship implements Serializable {} @Entity @PrimaryKeyJoinColumn public class Titanic extends Ship {}
-
Table per concrete class.
@Entity @Inheritance(strategy = InheritanceType.TABLE_PER_CLASS) public class Aeroplane implements Serializable {}
-
@DiscriminatorColumn: As the name suggests this column is the descriminator and this annotation specifies the discriminator column for the SINGLE_TABLE and JOINED Inheritance mapping strategies.
@Entity @Inheritance(strategy=InheritanceType.SINGLE_TABLE) @DiscriminatorColumn(name="cartype", discriminatorType=DiscriminatorType.STRING )
Это все, что касается аннотаций JPA и Hibernate. Ссылка: Документация по Hibernate API