JPA简介:
JPA全称Java Persistence API。JPA通过JDK5.0注解或XML描述对象——关系表的映射关系,并将运行期的实体对象持久化到数据库中。
JPA的总体思想和现有Hibernate、TopLink、JDP等ORM框架大体一致。总的来说,JPA包括以下3方面的技术:
(1)ORM映射元数据
JPA支持XML和JDK5.0注解两种元数据的形式,元数据描述对象和表之间的映射关系,框架据此将实体对象持久化到数据库表中;
(2)JPA的API
用来操作实体对象,执行CRUD操作,框架在后台替我们完成所有的事情,开发者从繁琐的JDBC和SQL代码中解脱出来。
(3)查询花语言
这是持久化操作中很重要的一个东西,通过面向对象而非面向数据库的查询语句查询数据,避免程序的SQL语句紧密耦合。
JPA基本注解:
@Entity
@Entity标注用韵实体类声明语句之前,之处该JAVA类为实体类,将映射到指定的数据库表。如声明一个实体类Customer,它将映射到数据库中的customer表上。
@Entity //标识这个pojo是一个jpa实体
public class Users implements Serializable {
}
@Table
当实体类与其映射的数据库表不同名时需要使用@Table标注说明,该标注与@Entity标注并列使用,置于实体类声明语句之前,可写于单独语句行,也可与声明语句同行。
@Table标注的常用选项是name,用于指定数据库的表名
@Table标注还有一个两个选项catalog和schema用于设置表所属的数据库目录或模式,通常为数据库名。uniqueConstraint选项用于设置约束条件,通常不须设置。
@Entity
@Table(name = "users") //指定表名为users
public class Users implements Serializable {
}
在加载数据的时候可以为其指定顺序,使用@OrderBy注解实现
@Table(name = "USERS")
public class User {
@OrderBy(name = "group_name ASC, name DESC")
private List books = new ArrayList();
}
@Table(name = "USERS")
public class User {
@OrderBy(name = "group_name ASC, name DESC")
private List books = new ArrayList();
}
@Id
@Id标注用于声明一个实体类的属性映射为数据库的主键列,该属性通常用于属性声明语句之前,可与声明语句同行,也可写在单独行上。
@Id标注也可置于属性的getter方法之前。
public class Users implements Serializable {
}
public class Users implements Serializable {
@Id
private String userCode;
@GenerateValue
@GenarateValue用于标注主键的生成策略,通过strategy属性指定。默认情况下,JPA自动选择一个最适合底层数据库的主键生成策略;
在javax.persistence.GenerationType中定义了以下几种可供选择的策略:
——IDENTITY:采用数据库ID自增长的方式来自增 主键字段
public class Users implements Serializable {
@Id
@GeneratedValue(strategy=GenerationType.IDENTITY)
@Column(name = "user_id", nullable = false)
private int userId;
——AUTO:JPA自动选择合适的策略,是默认选项
——SEQUENCE:通过序列产生主键,通过@Sequencegenerator注解指定序列名,MySQL不支持这种方式
public class Users implements Serializable {
@Id
@GeneratedValue(strategy=GenerationType.SEQUENCE)
@SequenceGenerator(name="seq_user")
@Column(name = "user_id", nullable = false)
private int userId;
——TABLE:通过表产生主键,框架借表模拟序列产生主键,使用该策略可以使应用更易于数据库移植
public class Users implements Serializable {
@Id
@GeneratedValue(strategy=GenerationType.TABLE)
@Column(name = "user_code", nullable = false)
private String userCode;
@Basic
@Basic表示一个简单的属性到数据库表的字段的映射,对于没有任何标注的getXxxx()方法,默认即为@Basic。
fetch:表示该属性的读取的策略,有EAGER和LAZY两种,分别表示主支抓取和延迟加载,默认为EAGER。
optional:表示该属性是否允许为null,默认为true。
@Column
当实体的属性与其映射的数据库表的列不同名时需要使用@Column标注说明,该属性通常置于实体的属性声明语句之前,还可与@Id标注一起使用。
@Colomn标注的columnDefinition属性:表示该字段在数据库中的实际类型,通常ORM框架可以根据属性类型自动判断数据库中字段的类型,但是对于Date类型扔无法确定数据库中字段类型到底是DATE、TIME还是TIMESTAMP。此外,String的默认映射类型为VARCHAR,如果将String类型映射到特定数据库的BLOB或TEXT字段类型。
@Column标注也可置于属性个getter方法之前。
通过@Column注解设置,包含的可设置属性如下
.name:字段名
.unique:是否唯一
.nullable:是否可以为空
.inserttable:是否可以插入
.updateable:是否可以更新
.columnDefinition: 定义建表时创建此列的DDL
.secondaryTable: 从表名。如果此列不建在主表上(默认建在主表),该属性定义该列所在从表的名字。
@Column(name = "user_code", nullable = false, length=32)//设置属性userCode对应的字段为user_code,长度为32,非空
private String userCode;
@Column(name = "user_wages", nullable = true, precision=12, scale=2)//设置属性wages对应的字段为user_wages,12位数字可保留两位小数,可以为空
@Transient
表示该属性并非一个到数据库表的字段的映射,ORM框架默认其注解为@Basic
@Temporal
在核心的Java API中并没有定义Date类型的精度,而在数据库中,表示Date类型的数据有DATE、TIME还是TIMESTAMP。
一对多双向映射关系
有T_One和T_Many两个表,他们是一对多的关系,注解范例如下
主Pojo
@Entity
@Table(name = "T_ONE")
public class One implements Serializable {
private static final long serialVersionUID = 1L;
@Id
@Column(name = "ONE_ID", nullable = false)
private String oneId;
@Column(name = "DESCRIPTION")
private String description;
@OneToMany(cascade = CascadeType.ALL, mappedBy = "oneId")//指向多的那方的pojo的关联外键字段
private Collection<Many> manyCollection;
子Pojo
@Entity
@Table(name = "T_MANY")
public class Many implements Serializable {
private static final long serialVersionUID = 1L;
@Id
@Column(name = "MANY_ID", nullable = false)
private String manyId;
@Column(name = "DESCRIPTION")
private String description;
@JoinColumn(name = "ONE_ID", referencedColumnName = "ONE_ID")//设置对应数据表的列名和引用的数据表的列名
@ManyToOne//设置在“一方”pojo的外键字段上
private One oneId;
一对多双向关联跟多对一是一样的,在多端生成一个外键,不生成第三张表来管理对应关系,由外键来管理对应关系