• 1. 概述

  • 2. 快速入门

  • 3. 分页操作

  • 4. 基于方法名查询

  • 5. 基于注解查询

  • 666. 彩蛋


5. 基于注解查询

虽然 Spring Data JPA 提供了非常强大的功能,可以满足绝大多数业务场景下的 CRUD 操作,但是可能部分情况下,我们可以使用在方法上添加 org.springframework.data.jpa.repository.@Query 注解,实现自定义的 SQL 操作。

如果是更新或删除的 SQL 操作,需要额外在方法上添加 org.springframework.data.jpa.repository.@Modifying 注解。

下面,我们来编写一个简单的示例。

5.1 UserRepository04

在 cn.iocoder.springboot.lab13.mybatis.repository 包路径下,创建 UserRepository04 接口。代码如下:

// UserRepository04.java

public interface UserRepository04 extends PagingAndSortingRepository<UserDOInteger{

    @Query("SELECT u FROM UserDO u WHERE u.username = ?1")
    UserDO findByUsername01(String username)// <1>

    @Query("SELECT u FROM UserDO u WHERE u.username = :username")
    UserDO findByUsername02(@Param("username") String username)// <2>

    @Query(value = "SELECT * FROM users u WHERE u.username = :username", nativeQuery = true)
    UserDO findByUsername03(@Param("username") String username)// <3>

    @Query("UPDATE UserDO  u SET u.username = :username WHERE u.id = :id")
    @Modifying
    int updateUsernameById(Integer id, String username)// <4>

}
  • <1> 处,使用 @Query 自定义了一个 SQL 操作,并且参数使用占位符(`?`) + 参数位置的形式。

  • <2> 处,和 <1> 类似,差异在于使用占位符(`:`) + 参数名字(需要使用 `@Param` 声明)的形式。

  • <3> 处,和 <2> 类似,差别在于我们增加了 nativeQuery = true ,表示在 @Query 自定义的是原生 SQL,而非在 <1> 和 <2> 自定义的是 JPQL 。进一步的说:

    • `<1>` 和 `<2>` 处,`FROM UserDO` ,使用的是实体名。

    • `<3>` 处,使用的是表名。

    • 对 JPQL 不是很了解的胖友,可以看看 《JPQL 的学习》 文章。

  • <4> 处,定义了更新操作,需要加上 @Modifying 注解。

  • 5.2 简单测试

  • 创建 UserRepository04Test 测试类,我们来测试一下简单的 UserRepository04 的每个操作。代码如下:

  • // UserRepository04Test.java

    @RunWith(SpringRunner.class)
    @SpringBootTest
    public class UserRepository04Test {

        @Autowired
        private UserRepository04 userRepository;

        @Test
        public void testFindIdByUsername01() {
            UserDO user = userRepository.findByUsername01("yunai");
            System.out.println(user);
        }

        @Test
        public void testFindIdByUsername02() {
            UserDO user = userRepository.findByUsername02("yunai");
            System.out.println(user);
        }

        @Test
        public void testFindIdByUsername03() {
            UserDO user = userRepository.findByUsername03("yunai");
            System.out.println(user);
        }

        @Test
        // 更新操作,需要在事务中。
        // 在单元测试中,事务默认回滚,所以胖友可能怎么测试,事务都不更新。
        @Transactional
        public void testUpdateUsernameById() {
            userRepository.updateUsernameById(5"yudaoyuanma");
        }

    }
  • 具体的,胖友可以自己跑跑,妥妥的。

  • 对于分页操作,需要在 @Query 编写查询分页列表和记录总数两条 SQL 。示例如下:

  • public interface UserRepository extends JpaRepository<UserLong{

      @Query(value = "SELECT * FROM USERS WHERE LASTNAME = ?1"// value 属性,编写查询分页列表的 SQL 。
        countQuery = "SELECT count(*) FROM USERS WHERE LASTNAME = ?1"// countQuery 属性,编写记录总数的 SQL 。
        nativeQuery = true)
      Page<User> findByLastname(String lastname, Pageable pageable);

    }
  • 666. 彩蛋

  • 本文仅仅是 Spring Data JPA 的简单入门,还有部分内容,胖友可以自己在去学习下:

  • 《Using JPA Named Queries》 ,可以使用 XML 自定义 SQL 操作。

  • 《Spring Data JPA 实现逻辑删除》 ,绝大多数业务场景下,我们不会使用 DELETE 物理删除,而是通过标志位进行逻辑删除。

  • 多表查询

    • 方式一:《JPA 多表查询的解决办法》

    • 方式二:《JPA 多表关联查询》

  • 《Spring Data JPA 使用 Example 快速实现动态查询》

    艿艿,如果在这种情况下,Repository 需要继承 JpaRepository 接口。

  • 如果胖友想找一个完整的,使用 JPA 的项目,可以看看 Apollo 。它是携程开源的配置中心,目前最好用的配置中心,基本没有之一,嘿嘿。

©著作权归作者所有:来自51CTO博客作者mb5ff80520dfa04的原创作品,如需转载,请注明出处,否则将追究法律责任

更多相关文章

  1. 芋道 Spring Boot MyBatis 入门(二)之 MyBatis + 注解
  2. JVM 线上故障排查基本操作
  3. 基于Spring Boot实现图片上传/加水印一把梭操作
  4. linux系统重启操作系统后报错提示An error occurred during the
  5. linux系统操作系统网卡漂移解决方案及问题原因
  6. linux操作系统可以ping通ssh连接无响应
  7. SpringBoot 中 @SpringBootApplication注解背后的三体结构探秘
  8. 操作系统分配存储时网络无法正常连接
  9. 一篇文章完全掌握 JavaScript 数组操作[每日前端夜话0x87]

随机推荐

  1. 将JavaScript命名空间拆分为多个文件
  2. 使用延迟到多个ajax调用的链循环
  3. Bootstrap面板:同一行上的文本和加号
  4. 使用Sinon模拟require()函数
  5. 在项目之间共享ASP.NET MVC部分视图
  6. 获取拆分字符串数组的最后一个元素
  7. 我可以更改javascript“this”的上下文吗
  8. FusionCharts的Line.swf做法,我想出现2条
  9. jQuery:执行一个函数AFTER toggleClass被
  10. jquery 更改angularJS input 内容导致绑