JPA规范(java持久化API)JPA和Hibernate等框架一样,都是java持久化解决方案,负责把数据保存到数据库。不同的是,JPA只是一种标注,规范,而不是框架。JPA自己没有具体的实现。
使用JPA后,程序不在依赖于某种ORM框架。如果原来用的JPA+Hibernate,则完全可以改为使用JPA+TopLink,只需要修改配置即可。
JPA通过注解来配置实体类和数据库的映射关系,下面来看一个具体的例子。
<span style="font-size:18px;">
import javax.persistence.Column;
import javax.persistence.Entity;
import javax.persistence.GeneratedValue;
import javax.persistence.GenerationType;
import javax.persistence.Id;
import javax.persistence.Table;
@Entity//表示实体类可以被持久化
@Table(name = "tb_person")//指定该实体类对应的数据库表
public class Person{
@Id//指定该列的主键
@GeneratedValue(strategy = GenerationType.AUTO)//主键类型,auto为增长类型
private Integer id;
@Column(name = "name")//指定该属性对应的数据库列名
private String name;
@Column(name = "<span style="font-family: Arial, Helvetica, sans-serif;">age</span>")</span>
<span style="font-size:18px;"> private int age;
public int getAge() {
return age;
}
public void setAge(int age) {
this.age = age;
}
public Integer getId() {
return id;
}
public void setId(Integer id) {
this.id = id;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
}</span>
实体类用java注解来配置也相当的简单。有一点需要注意的是实体类主键最好使用可以为null的类型,例如Integer Long等
JPA的API
JPA的API都位于javax.persistence包下。
1 获取EntityManager
<span style="font-size:18px;">public void init() throws ServletException {
if (emFactory == null) {
emFactory = Persistence.createEntityManagerFactory("jpa");
}
}</span>
参数jpa在persistence.xml中配置
<span style="font-size:18px;"> public void add(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
EntityManager em = emFactory.createEntityManager();
Person p<span style="font-family: Arial, Helvetica, sans-serif;">erson </span>= new Person();
person.setName("Person" + new Random().nextInt(10));
person.setAge(15 + new Random().nextInt(10));
em.getTransaction().begin();
em.persist(student);
em.getTransaction().commit();
em.close();
this.list(request, response);
}</span>
实体类的状态
跟Hibernate一样,JPA中的实体类也包括几种状态
jpa 实体生命周期有四种状态
-
(临时状态)Transient:瞬时对象,尚未有id,还未和Persistence Context建立关联的对象。
-
(持久化状态)Persistent:持久化受管对象,有id值,已经和Persistence Context建立了关联的对象。持久化状态的对象可以执行任何有关数据库的操作。
-
(分离状态)Datached:游离态离线对象,有id值,但没有和Persistence Context建立关联的对象。无法进行数据库操作
-
Removed:删除的对象,有id值,尚且和Persistence Context有关联,但是已经准备好从数据库中删除
Managed状态下的数据保存,更新以及删除数据下的Removed状态,数据都不会立即更新到数据库,只有当你事务提交或者em.flush(),才会立即更新到数据库。
Datached的状态,可以调用em.merge()方法,这个方法会根据实体类的id来更新数据库数据,这时实体类变成了Managed状态。
2 持久化persist()persist()将临时状态的对象保存进数据库。因为持久化时涉及数据库的写入,因此需要用到事物
<span style="font-size:18px;"> EntityManager em = emFactory.createEntityManager();
Student student = new Student();
student.setName("Student " + new Random().nextInt(10));
student.setAge(15 + new Random().nextInt(10));
em.getTransaction().begin();
em.persist(student);
em.getTransaction().commit();
em.close();</span>
3 查找find()与getReference()
find()与getReference()都能查找对象,不同的是当对象不存在时,find会返回空getReference会抛出javax.persistence.EntityNotFoundException异常
4 保存merge()
merge(Object obj)将修改后的对象保存进数据库。merge时要用到事务。
<span style="font-size:18px;"> EntityManager em = emFactory.createEntityManager();
em.getTransaction().begin();//开启事务</span>
<span style="font-size:18px;"></span><pre name="code" class="java"><span style="font-size:18px;"><span style="white-space:pre"> </span>Student student = em.find(Student.Class,1);//查询</span>
student.setName("aa");em.merge(student);//保存修改em.getTransaction().commit();//提交事物em.close();
5 remove(object obj)将对象从数据库中删除,需要开启事务
6 刷新refresh()和包含contains()
refresh(Object obj)从新从数据库中读取数据。contains(Object obj)判断对象是否在数据库返回true,false
7 查询 creatQuery()
creatQuery()返回javax.persistence.Query对象。Query使用JPQL(java persistence query language)语句进行查询,类似hibernate的HQL。
<span style="font-size:18px;">EntityManager em = emFactory.createEntityManager();
List studentList = em.createQuery(
" select s from Student s order by s.id desc ").setMaxResults(
100).getResultList();</span>
<span style="font-size:18px;"><span style="white-space:pre"> </span>em.close();</span>
8 写入数据库flush()
执行persist(),merge()时,数据不会立即写入数据库中,而是由JPA缓存起来,在进行flush()时写入。在事务提交时,JPA会自动执行flush()一次性保存所有数据。如果需要将数据立即写入数据库,可以手动flush()。
9 清除对象 clear()
clear()清除所有被监视的(Session中的)实体类对象