天天看點

SpringDataJPA之JpaRepository和JpaSpecificationExecutor接口

文章目錄

   JpaRepository

       1.建立接口

       2.單元測試

   JpaSpecificationExecutor

       2.具體功能

           2.1 單條件查詢

           2.2 多條件查詢

           2.3 分頁

           2.4 排序

           2.5 分頁排序

 本文我們來介紹下SpringDataJPA繼承結構中剩下的兩個接口

JpaRepository

 JpaRepository 接口是我們開發時使用的最多的接口。其特點是可以幫助我們将其他接口的方法的傳回值做适配處理。可以使得我們在開發時更友善的使用這些方法。

1.建立接口

/**
 * SpringDataJPA 實作JpaRepository
 * 泛型 第一個參數是對應的Pojo類型
 *      第二個參數是注解的包裝類型
 */
public interface UserDao extends JpaRepository<Users,Integer> {

}      

2.單元測試

/**
 * @program: spring-data-jpa
 * @description: 單元測試
 * @author: 波波烤鴨
 * @create: 2019-05-18 09:48
 */
@RunWith(SpringJUnit4ClassRunner.class)
@ContextConfiguration("classpath:applicationContext.xml")
public class TestDemo {

    @Autowired
    private UserDao usersDao;


    /**
     * 添加使用者
     */
    @Test
    @Transactional// 在測試類對于事務送出方式預設的是復原。
    @Rollback(false)//取消自動復原
    public void testInsertUsers(){
        Users users = new Users();
        users.setUserage(20);
        users.setUsername("張三-jpa");
        this.usersDao.save(users);
    }
}      

JpaSpecificationExecutor

 完成多條件查詢,并且支援分頁與排序。

 JpaSpecificationExecutor接口不能夠單獨使用,需要和其他接口一塊使用,如下

/**
 * JpaSpecificationExecutor 接口講解
 * @author Administrator
 *注意:JpaSpecificationExecutor<Users>:不能單獨使用,需要配合着 jpa 中的其他接口一起使用
 */
public interface UserDao extends JpaRepository<Users, Integer>
                    , JpaSpecificationExecutor<Users> {

}      

2.具體功能

2.1 單條件查詢

/**
*  單條件查詢
* 需求:根據使用者姓名查詢資料
*/
@Test
public void test1(){
   Specification<Users> spec = new Specification<Users>() {
       /**
        * @return Predicate:定義了查詢條件
        * @param Root<Users> root:根對象。封裝了查詢條件的對象
        * @param CriteriaQuery<?> query:定義了一個基本的查詢.一般不
       使用
        * @param CriteriaBuilder cb:建立一個查詢條件
        */
       @Override
       public Predicate toPredicate(Root<Users> root,
                                    CriteriaQuery<?> query, CriteriaBuilder cb) {
           Predicate pre = cb.equal(root.get("username"), "王五");
           return pre;
       }
   };
   List<Users> list = this.usersDao.findAll(spec);
   for (Users users : list) {
       System.out.println(users);
   }
}      

2.2 多條件查詢

 多條件查詢有兩種方式,具體如下

/**
 * 多條件查詢 方式一
 * 需求:使用使用者姓名以及年齡查詢資料
 */
@Test
public void test2() {
    Specification<Users> spec = new Specification<Users>() {
        @Override
        public Predicate toPredicate(Root<Users> root,
                                     CriteriaQuery<?> query, CriteriaBuilder cb) {
            List<Predicate> list = new ArrayList<>();
            list.add(cb.equal(root.get("username"), "王五"));
            list.add(cb.equal(root.get("userage"), 24));
            //此時條件之間是沒有任何關系的。
            Predicate[] arr = new Predicate[list.size()];
            return cb.and(list.toArray(arr));
        }
    };
    List<Users> list = this.usersDao.findAll(spec);
    for (Users users : list) {
        System.out.println(users);
    }
}

/**
 * 多條件查詢 方式二
 * 需求:使用使用者姓名或者年齡查詢資料
 */
@Test
public void test3(){
    Specification<Users> spec = new Specification<Users>() {
        @Override
        public Predicate toPredicate(Root<Users> root,
                                     CriteriaQuery<?> query, CriteriaBuilder cb) {

            return cb.or(cb.equal(root.get("username"),"王五 "),cb.equal(root.get("userage"), 25));
        }
    };
    List<Users> list = this.usersDao.findAll(spec);
    for (Users users : list) {
        System.out.println(users);
    }
}      

2.3 分頁

/**
 * 需求:查詢王姓使用者,并且做分頁處理
 */
@Test
public void test4(){
    //條件
    Specification<Users> spec = new Specification<Users>() {
        @Override
        public Predicate toPredicate(Root<Users> root,
                                     CriteriaQuery<?> query, CriteriaBuilder cb) {
            return cb.like(root.get("username").as(String.class), "王%");
        }
    };
    //分頁
    Pageable pageable = new PageRequest(2, 2);
    Page<Users> page = this.usersDao.findAll(spec, pageable);
    System.out.println("總條數:"+page.getTotalElements());
    System.out.println("總頁數:"+page.getTotalPages());
    List<Users> list = page.getContent();
    for (Users users : list) {
        System.out.println(users);
    }
}      

2.4 排序

/**
 * 需求:查詢資料庫中王姓的使用者,并且根據使用者 id 做倒序排序
 */
@Test
public void test5(){
    //條件
    Specification<Users> spec = new Specification<Users>() {
        @Override
        public Predicate toPredicate(Root<Users> root,
                                     CriteriaQuery<?> query, CriteriaBuilder cb) {
            return cb.like(root.get("username").as(String.class),
                    "王%");
        }
    };
    //排序
    Sort sort = new Sort(Sort.Direction.DESC,"userid");
    List<Users> list = this.usersDao.findAll(spec, sort);
    for (Users users : list) {
        System.out.println(users);
    }
}      

2.5 分頁排序

/**
 * 需求:查詢資料庫中王姓的使用者,做分頁處理,并且根據使用者 id 做倒序排序
 */
@Test
public void test6(){
    //排序等定義
    Sort sort = new Sort(Sort.Direction.DESC,"userid");
    //分頁的定義
    Pageable pageable = new PageRequest(0,2, sort);
    //查詢條件
    Specification<Users> spec = new Specification<Users>() {
        @Override
        public Predicate toPredicate(Root<Users> root,
                                     CriteriaQuery<?> query, CriteriaBuilder cb) {
            return cb.like(root.get("username").as(String.class),
                    "王%");
        }
    };
    Page<Users> page = this.usersDao.findAll(spec, pageable);
    System.out.println("總條數:"+page.getTotalElements());
    System.out.println("總頁數:"+page.getTotalPages());
    List<Users> list = page.getContent();
    for (Users users : list) {
        System.out.println(users);
    }
}      

如此我們對于單表的相關操作通過JpaSpecificationExecutor接口和JpaRepository接口就都可以實作了~

繼續閱讀