jpql介绍和基本语法

jpql与SQL的区别就是SQL是面向对象关系数据库,他操作的是数据表和数据列,而jpql操作的对象是实体对象和实体属性

格式:select 实体别名.属性名, 实体别名.属性名 from 实体名 as 实体别名 where 实体别名.实体属性 op 比较值

案例 :select p.name from book as p

注意:jpql是面向实体,查询的是类和类中的属性,而不是数据库;jpql不支持添加操作!

使用方式:

@Query(value="select menu from SysMenu menu")

这里的****SysMenu 是实体名

其中 select menu 可以省略,直接 写 from xxx

jpql传参

占位符传参

  • jpql默认使用 ?表示占位符 ,此时参数的顺序和jpql语句的顺序必须一致,如下代码:

value中的menuId对应对应参数 Long menuId

//select menu也可以不写 jpa会自动填充
    @Query(value = " from SysMenu menu where menu.menuId=?1")
    SysMenu getSys(Long menuId);
  • 使用?索引方式传参

当参数和jpql语句顺序不一致时,可以使用?索引的方式指定哪个占位符使用哪一个参数

@Query(value = " from SysMenu menu where menu.menuName=?2 and menu.menuId=?1 ")
    SysMenu getSysZwf(Long menuId, String menuName);

@Param()方式传参

基本语法

此方式和mybatis中类似,即指定参数的别名,但是参数绑定是使用 : 的方式;如下:

@Query(value = "from User u where u.name=:name and u.email=:email")
User findByNameAndEmail(@Param("name")String name, @Param("email")String email);

like方式查询

// like 查询
@Query(value = "from User u where u.name like %:nameLike%")
 List<User> findByNameLike(@Param("nameLike")String nameLike);

传入集合 in 方式等

@Query(value = "from User u where u.name in :nameList")
List<User> findByNameIn(@Param("nameList")Collection<String> nameList);

传入对象

@Query(value = "from User u where u.name=:#{#usr.name} and u.password=:#{#usr.password}")
User findByNameAndPassword(@Param("usr")User usr);

jpql 分页查询

使用jpql分页是在接口上传入 Pageable参数即可自动实现

  • 接口如下:
//jpql 分页查询
@Query(value = " from SysMenu menu where menu.menuName like :menuName%  ")
Page<SysMenu> getSysPage(Pageable pageable, @Param("menuName") String menuName);
Page<SysMenu> sysPage = dao.getSysPage(
                PageRequest.of(0, 1, Sort.by(Sort.Direction.DESC, "menuId")),
                "测试");
        System.out.println(sysPage);
        System.out.println(sysPage.getContent());
        System.out.println(sysPage.getTotalElements());

PageRequest 是Pageable的实现类

Sort.by指定排序方式和排序字段 

jpql执行更新和删除操作

  • 使用jpql执行更新和删除操作 ,接口需要增加注解 @Modifying,且需要加入事务支持,否则会报错 *Executing an update/delete query; nested exception is javax.persistence.TransactionRequiredException;*
  • 操作的返回值为int类型;
  • 还需要增加注解 @Rollback(value = false) ,因为pa事务默认在更新或删除成功后会自动回滚,,此注解设置事务不自动回滚
//使用jpql执行更新操作
    @Query(value = "update  SysMenu  set menuName=?2 where  menuId=?1")
    @Modifying
    int updateMenu(Long menuId, String menuName);
@Test
    @Transactional
    @Rollback(value = false)
    public void  testUpdateJpql(){
       int count = dao.updateMenu(121l, "测试更新");
        System.out.println(count);

    }

这个里面直接要获取分页对象里面的内容通过pag.getContent,来进行获取

通过getTotalElements来获取对应分页的总数

注意:需要这两个注解@Transactional @Rollback(value = false)