1、基本使用步骤:
1)引入jpa相关依赖
2)建立数据库表与项目实体类的关系 --通过注解建立实体类与表、表中字段的关系
3)编写继承 Repository/CrudRepository/PagingAndSortingRepository/JpaRepository/JPASpecificationExecutor接口的实体类操作接口
- Repository:
提供了方法名称命名查询方式:方法名称必须要遵循驼峰式命名规则,findBy(关键字)+属性名称(首字母大写)+查询条件(首字母大写)
提供了基于@Query注解查询与更新:在方法上使用该注解编写SQL查询/更新语句
- CrudRepository:主要是完成一些增删改查的操作
- PagingAndSortingRepository:提供了分页与排序的操作
- JpaRepository:继承了PagingAndSortingRepository。对继承的父接口中方法的返回值进行适配
- JPASpecificationExecutor: 提供了多条件查询的支持,并且可以在查询中添加排序与分页。注意JPASpecificationExecutor是单独存在的。完全独立,
继承关系说明: Repository<-CrudRepository<-PagingAndSortingRepository<-JpaRepository
3.1)JPASpecificationExecutor使用说明
JpaSpecificationExecutor接口的使用一般要和Repository体系的接口一起使用,使用JpaSpecificationExecutor对象必须实现Repository体系的接口。
public interface JpaSpecificationExecutor<T> {
T findOne(Specification<T> var1); //查询一个
List<T> findAll(Specification<T> var1);//条件产讯
Page<T> findAll(Specification<T> var1, Pageable var2);//分页查询
List<T> findAll(Specification<T> var1, Sort var2);//排序查询
long count(Specification<T> var1);//计数查询
}
参数说明:
Specifcation对象:该对象是一个接口,通过该接口封装查询条件。
Specifcation源码
public interface Specification<T> {
Predicate toPredicate(Root<T> var1, CriteriaQuery<?> var2, CriteriaBuilder var3);
}
Specifcation接口匿名实现类定义示例
@Test
public void test1(){
Specification spc = new Specification(){
@Override
/**
* @description:
* @param root 根参数,通过次对象获取实体对象字段进行条件的设置
* @param criteriaQuery 定义一个基本的查询
* @param criteriaBuilder 创建一个查询条件
* @return: javax.persistence.criteria.Predicate
*/
public Predicate toPredicate(Root root, CriteriaQuery criteriaQuery, CriteriaBuilder criteriaBuilder) {
return criteriaBuilder.equal(root.get("username"),"AAA");
}
};
}
使用JpaSpecificationExecutor对象进行条件查询基本步骤:
- 使用JpaSpecificationExecutor接口对应的dao调用相应的条件查询方法
- 在方法中传入指定的形参,其中Specifcation接口对应的形参一般传入该接口的匿名实现类
- 在匿名实现类中重写toPredicate()方法,返回一个条件对象Predicate
3.1.1)单条件查询
使用CriteriaBuilde构建单个条件,如上述展示的条件查询
3.1.2)多条件查询
方式一:使用参数Predicate进行参数的设置完成将多个的条件封装成数组的形式传递给接收多个参数的方法完成多条件查询
/**
* 多条件查询使用Predicate集合进行添加条件,将数据填充到集合内
* Predicate and(Predicate... var1);接收可变形参将集合转成数组即可(可以直接使用数组)
*/
@Test
public void test3(){
Specification spc = (x,y,z)->{
ArrayList<Predicate> list = new ArrayList<>();
list.add(z.equal(x.get("username"),"AAA"));
list.add(z.equal(x.get("password"),"123"));
Predicate[] predicates = new Predicate[list.size()];
return z.and(list.toArray(predicates));
};
List<Users> list = this.userDaoFive.findAll(spc);
list.stream()
.forEach(System.out::println);
}
方式二
直接在条件查询内写入查询的条件即可SpringData 会自动的将条件进行拼接
缺点:如果出现条件较长的话会出现代码过长的问题
/**
* 多条件查询方式二
*/
@Test
public void test4(){
Specification spc = (x,y,z)->z.and(z.equal(x.get("username"),"AAA"),z.equal(x.get("password"),"123"));
List<Users> list = this.userDaoFive.findAll(spc);
list.stream()
.forEach(System.out::println);
}
4)调用上述步骤接口中的方法完成增删改查
2. 基本操作:
按照步骤1完成增删改查
3.关联映射操作
3.1)一对多的关联关系
需求:角色与用户的一对多的关联关系
角色:一方
用户:多方
假设:外键在用户一侧 //外键在谁那里就由谁说明外键之间的映射关系->通过@JoinColumn注解
增删改查步骤:
1)实体类处理:在角色,用户的关联字段上使用@ManyToOne注解说明关联关系,并在用户的关联字段上通过@JoinColumn说明两张表映射关系。
2)通过dao接口调用相应方法完成crud
3.2)多对多的关联关系
角色与菜单多对多关联关系
菜单:多方
角色:多方
说明:多对多关系中,由一张中间表完成二者的关系映射。此处的中间表字段为:菜单id,角色id
假设:角色表中的主键关联中间表的外键 //外键在谁那里就由谁说明外键之间的映射关系->通过@JoinTable,@JoinColumn注解
增删改查步骤:
1)实体类处理:在角色,用户的关联字段上使用@ManyToMany注解说明关联关系,并在角色的关联字段上通过@JoinTable,@JoinColumn说明中间表中的字段映射关系。
2)通过dao接口调用相应方法完成crud
3)自定义删改操作
在@Query注解内编写SQL语句,并且在方法上增加@Modify注解,告诉JPA执行的是更改操作
说明: update操作的返回类型只能是int这样的数字型或null
@Modifying
@Query(value = "UPDATE am_app_form SET app_status = :status, app_status_info = :statusInfo WHERE app_id = :id", nativeQuery = true)
void updateStatusById(@Param("id") Long id, @Param("status") String status, @Param("statusInfo") String statusInfo);