11.7 数据访问层代码

在Spring Data JPA中,我们只需要实现接口CrudRepository<T, ID>即可获得一个拥有基本CRUD操作的接口实现了:

  1. interface ArticleRepository : CrudRepository<Article, Long>

JPA会自动实现ArticleRepository接口中的方法,不需要我们写基本的CRUD操作代码。它的常用的基本CRUD操作方法的简单说明如下表:

方法 功能说明
S save(S entity) 保存给定的实体对象,我们可以使用这个保存之后返回的实例进行进一步操作(保存操作可能会更改实体实例)
findById(ID id) 根据主键id查询
existsById(ID id) 判断是否存在该主键id的记录
findAll() 返回所有记录
findAllById(Iterable ids) 根据主键id集合批量查询
count() 返回总记录条数
deleteById(ID id) 根据主键id删除
deleteAll() 全部删除

当然,如果我们需要自己去实现SQL查询逻辑,我们可以直接使用@Query注解。

  1. interface ArticleRepository : CrudRepository<Article, Long> {
  2. override fun findAll(): MutableList<Article>
  3. @Query(value = "SELECT * FROM blog.article where title like %?1%", nativeQuery = true)
  4. fun findByTitle(title: String): MutableList<Article>
  5. @Query("SELECT a FROM #{#entityName} a where a.content like %:content%")
  6. fun findByContent(@Param("content") content: String): MutableList<Article>
  7. @Query(value = "SELECT * FROM blog.article where author = ?1", nativeQuery = true)
  8. fun findByAuthor(author: String): MutableList<Article>
  9. }

11.7.1 原生SQL查询

其中,@Query注解里面的value的值就是我们要写的 JP QL语句。另外,JPA的EntityManager API 还提供了创建 Query 实例以执行原生 SQL 语句的createNativeQuery方法。

默认是非原生的JP QL查询模式。如果我们想指定原生SQL查询,只需要设置
nativeQuery=true即可。

11.7.2 模糊查询like写法

另外,我们原生SQL模糊查询like语法,我们在写sql的时候是这样写的

  1. like '%?%'

但是在JP QL中, 这样写

  1. like %?1%

11.7.3 参数占位符

其中,查询语句中的 ?1 是函数参数的占位符,1代表的是参数的位置。

11.7.4 JP QL中的SpEL

另外我们使用JPA的标准查询(Criteria Query):

  1. SELECT a FROM #{#entityName} a where a.content like %:content%

其中的#{#entityName} 是SpEL(Spring表达式语言),用来代替本来实体的名称,而Spring data jpa会自动根据Article实体上对应的默认的 @Entity class Article ,或者指定@Entity(name = "Article") class Article 自动将实体名称填入 JP QL语句中。

通过把实体类名称抽象出来成为参数,帮助我们解决了项目中很多dao接口的方法除了实体类名称不同,其他操作都相同的问题。

11.7.5 注解参数

我们使用@Param("content") 来指定参数名绑定,然后在JP QL语句中这样引用:

  1. :content

JP QL 语句中通过”: 变量”的格式来指定参数,同时在方法的参数前面使用 @Param 将方法参数与 JP QL 中的命名参数对应。