Spring Data JPA数据持久化
JPA简介
- JPA(Java Persistence API)定义了对象关系映射(ORM)以及实体对象持久化的标准接口
- JPA是用于管理Java EE和Java SE环境中的持久化,以及对象/关系映射的Java API
- JPA是一个基于ORM(Object Relational Mapping)的标准规范,所谓规范是只定义标准规则(如:接口、注解),不提供具体实现
- 主要实现
- Hibernate、Eclipse和OpenJPA
JPA提供的技术
JPA所维护的核心是实体(Entity bean),而它是通过一个持久化上下文(Persistence Context)来使用的。
- ORM映射元数据:JPA支持XML和JDK 5.0注解两种元数据的形式,元数据描述对象和表之间的映射关系,框架据此将实体对象持久化到数据库表中,在SpringBoot中主要通过直接实现
- JPA 的API:定义规范,以操作实体对象,执行CRUD操作,来完成对象的持久化和查询,框架在后台替我们完成所有的事情,开发者从繁琐的JDBC和SQL代码中解脱出来
- 查询语言:通过面向对象而非面向数据库的查询语言查询数据,避免程序的SQL语句紧密耦合。定义JPQL(Java Persistence Query Language)和Criteria两种查询方式,约定了面向对象的查询原因JPQL,通过这层关系可以实现比较灵活的查询
JPA核心概念
实体
- 实体表示关系数据库中的表
- 每个实体实例对应于该表中的行
- 类必须用javax.persistence.Entity注解
- 类必须有一个public或protected的无参数的构造函数
- 实体实例被当做值以分离对象方式进行传递(例如通过会话bean的远程业务接口),则该类必须实现Serializable接口
- 唯一的对象标识符:简单主键(javax.persistence.Id)、复合主键(javax.persistence.EmbeddedId和javax.persistence.IdClass)(简而言之,必须有一个id)
关系
- 一对一:@OneToOne
- 一对多:@OneToMany
- 多对一:@ManyToOne
- 多对多:@ManyToMany
EntityManager
EntityManager接口:是应用程序操纵持久化数据的接口,用于增删改查
- 定义用于持久性上下文进行交互的方法
- 创建和删除持久实体实例,通过实体的主键查找实体
- 允许在实体上运行查询
EntityManager称为实体管理器,由EntityManagerFactory所创建
获取EntityManager实例:
@PersistenceUnit EntityManagerFactory emf; EntityManager emf; @Resource UserTranscation utx; ... //通过EntityManagerFactory获取EntityManager em=emf.createEntityManager(); try{ //事务开启 utx.begin(); em.persist(SomeEntity); em.merge(AnotherEntity); em.remove(ThirdEntity); //事务提交 utx.commit(); }catch(Exception e){ utx.rollback(); }
查找实体:
@PersistenceContext EntityManager em; public void enterOrder(int custID,CustomerOrder newOrder){ Customer cust=em.find(Customer.class,CustID); cust.getOrders().add(newOrder); newOrder.setCustomer(cust); }
补充:间歇性忘记ORM,说明没有理解ORM的思想,所以在此补充ORM
ORM思想概述
- 建立两个映射关系
- 实体类和表的映射关系
- 实体类中属性和表中字段的映射关系
- 不再重点关注SQL语句
- 主要目的:操作实体类相当于操作数据库
- ORM框架:
- Mybatis
- Hibernate
Spring Data JPA简介
- 是Spring Data家族的一部分
- 对基于JPA的数据访问层的增强支持
- 更容易构建基于使用Spring数据访问技术栈的应用程序
常用接口
- CrudRepository 该接口提供了11个常用操作方法
- PagingAndSortingRepostiory 该接口继承了CrudRepository接口,提供了两个方法,实现了分页和排序的功能
- JpaPepository 该接口继承了PagingAndSortingRepository接口。同时也继承QueryByExampleExecutor接口,这是个用“实例”进行查询的接口
@NoRepositoryBean public interface CrudRepository<T, ID extends Serializable> extends Repository<T, ID> { <S extends T> S save(S entity);//保存 <S extends T> Iterable<S> save(Iterable<S> entities);//批量保存 T findOne(ID id);//根据id 查询一个对象。返回对象本身,当对象不存在时,返回null Iterable<T> findAll();//查询所有的对象 Iterable<T> findAll(Iterable<ID> ids);//根据id列表 查询所有的对象 boolean exists(ID id);//根据id 判断对象是否存在 long count();//计算对象的总个数 void delete(ID id);//根据id 删除 void delete(T entity);//删除一个对象 void delete(Iterable<? extends T> entities);//批量删除,集合对象(后台执行时,一条一条删除) void deleteAll();//删除所有 (后台执行时,一条一条删除) }
@NoRepositoryBean public interface PagingAndSortingRepository<T, ID extends Serializable> extends CrudRepository<T, ID> { Iterable<T> findAll(Sort sort);// 仅排序 Page<T> findAll(Pageable pageable);// 分页和排序 }
@NoRepositoryBean public interface JpaRepository<T, ID extends Serializable> extends PagingAndSortingRepository<T, ID>, QueryByExampleExecutor<T> { List<T> findAll(); //查询所有对象,返回List List<T> findAll(Sort sort); //查询所有对象,并排序,返回List List<T> findAll(Iterable<ID> ids); //根据id列表 查询所有的对象,返回List void flush(); //强制缓存与数据库同步 <S extends T> List<S> save(Iterable<S> entities); //批量保存,并返回对象List <S extends T> S saveAndFlush(S entity); //保存并强制同步数据库 void deleteInBatch(Iterable<T> entities); //批量删除 集合对象(后台执行时,生成一条语句执行,用多个or条件) void deleteAllInBatch();//删除所有 (执行一条语句,如:delete from user) T getOne(ID id); //根据id 查询一个对象,返回对象的引用(区别于findOne)。当对象不存时,返回引用不是null,但各个属性值是null @Override <S extends T> List<S> findAll(Example<S> example); //根据实例查询 @Override <S extends T> List<S> findAll(Example<S> example, Sort sort);//根据实例查询,并排序。 }