Spring JPA find單表查詢方法示例詳解
一、findById(ID id)
通過id進行單條查詢,先看看 findById(ID id) 的源碼
@Override public Optional<T> findById(ID id) { Assert.notNull(id, ID_MUST_NOT_BE_NULL); Class<T> domainType = getDomainClass(); if (metadata == null) { return Optional.ofNullable(em.find(domainType, id)); } LockModeType type = metadata.getLockModeType(); Map<String, Object> hints = new HashMap<>(); getQueryHints().withFetchGraphs(em).forEach(hints::put); return Optional.ofNullable(type == null ? em.find(domainType, id, hints) : em.find(domainType, id, type, hints)); }
從源碼可以看出,最終調用的是EntityManager的find方法,EntityManager是jpa用來做持久化的,有空可以跟大傢探討一下!
下面是控制臺的輸出:
Hibernate: select user0_.id as id1_0_0_, user0_.age as age2_0_0_, user0_.name as name3_0_0_ from user user0_ where user0_.id=?
二、findAll()
查找所有的數據,源碼如下:
@Override public List<T> findAll() { return getQuery(null, Sort.unsorted()).getResultList(); }
從源碼可以看出,最終調用瞭org.hibernate.Query
的getResultList方法。
控制臺輸出如下:
Hibernate: select user0_.id as id1_0_, user0_.age as age2_0_, user0_.name as name3_0_ from user user0_
三、findAllById(Iterable<ID> ids)
通過ids進行多條查詢,源碼如下:
@Override public List<T> findAllById(Iterable<ID> ids) { Assert.notNull(ids, "Ids must not be null!"); if (!ids.iterator().hasNext()) { return Collections.emptyList(); } if (entityInformation.hasCompositeId()) { List<T> results = new ArrayList<>(); for (ID id : ids) { findById(id).ifPresent(results::add); } return results; } Collection<ID> idCollection = Streamable.of(ids).toList(); ByIdsSpecification<T> specification = new ByIdsSpecification<>(entityInformation); TypedQuery<T> query = getQuery(specification, Sort.unsorted()); return query.setParameter(specification.parameter, idCollection).getResultList(); }
從源碼可以看出,跟findAll方法一樣,最終調用的是org.hibernate.Query
的getResultList方法,隻不過加瞭id的集合。
控制臺打印如下:
Hibernate: select user0_.id as id1_0_, user0_.age as age2_0_, user0_.name as name3_0_ from user user0_ where user0_.id in (? , ?)
control層
@GetMapping("findAllById") public List<User> findAllById(Integer[] ids) { return userService.findAllById(Arrays.asList(ids)); }
四、findAll(Sort sort) 單調排序
根據sort對象對所有數據進行相應的排序
@Override public List<T> findAll(Sort sort) { return getQuery(null, sort).getResultList(); }
這個源碼也是沒啥可看的!需要註意的就是這個sort對象。
這個sort對象是需要我們自己去創建,然後根據自己的訴求傳入相應的參數。這裡我們就是使用sort.by來實現吧(也可以通過其他方法)
sort.by 源碼
/** * Creates a new {@link Sort} for the given {@link Order}s. * * @param direction must not be {@literal null}. * @param properties must not be {@literal null}. * @return */ public static Sort by(Direction direction, String... properties) { Assert.notNull(direction, "Direction must not be null"); Assert.notNull(properties, "Properties must not be null"); Assert.isTrue(properties.length > 0, "At least one property must be given"); return Sort.by(Arrays.stream(properties)// .map(it -> new Order(direction, it))// .collect(Collectors.toList())); }
可以看到我們需要傳入兩個參數,分別是 direction 和 properties:
direction 是排序方向(升序或降序)
properties 是排序的對象,是個數組(可以是單個也可以是多個)
control層
@GetMapping("findAllSort") public List<User> findAllSort(String ascOrDesc, String[] para) { Sort sort; if(ascOrDesc.toLowerCase().equals("desc")){ sort = Sort.by( Sort.Direction.DESC, para); }else { sort = Sort.by( Sort.Direction.ASC, para); } return userService.findAllSort(sort); }
請求 findAllSort?ascOrDesc=desc¶=age,name
,對 age 和 name 進行降序排序,結果如下:
[{ "id": 21, "name": "bb", "age": 12 }, { "id": 22, "name": "cc", "age": 11 }, { "id": 20, "name": "aa", "age": 11 }]
控制臺輸出如下:
Hibernate: select user0_.id as id1_0_, user0_.age as age2_0_, user0_.name as name3_0_ from user user0_ order by user0_.age desc, user0_.name desc
五、findAll(Sort sort) 多參數排序
上面的隻能進行單調的排序,就是說多個對象隻能一同升序或者降序;而在實際需求中,有時候還需要對多個對象,進行不同的排序,有的升序,有的降序。想要完成這樣的查詢,我們還是需要依靠sort對象去實現。sort.by 的入參中還有可以傳 order 數組和列表,我們就利用數組和列表對數據進行多參數的多樣排序,話不多說,直接上碼。
Sort by 源碼
/** * Creates a new {@link Sort} for the given {@link Order}s. * * @param orders must not be {@literal null}. * @return */ public static Sort by(List<Order> orders) { Assert.notNull(orders, "Orders must not be null"); return orders.isEmpty() ? Sort.unsorted() : new Sort(orders); } /** * Creates a new {@link Sort} for the given {@link Order}s. * * @param orders must not be {@literal null}. * @return */ public static Sort by(Order... orders) { Assert.notNull(orders, "Orders must not be null"); return new Sort(Arrays.asList(orders)); }
control 層
@GetMapping("findAllMoreSort") public List<User> findAllMoreSort(String[] sorts,String[] paras) { int length = sorts.length; //Sort.Order[] orders = new Sort.Order[length]; List<Sort.Order> listOrder = new ArrayList<>(); for(int i=0; i<length; i++){ // orders[i] = new Sort.Order(sorts[i].toLowerCase().equals("asc") ? // Sort.Direction.ASC : Sort.Direction.DESC, paras[i]); listOrder.add(new Sort.Order(sorts[i].toLowerCase().equals("asc") ? Sort.Direction.ASC : Sort.Direction.DESC, paras[i])); } //Sort sort = Sort.by(orders); Sort sort = Sort.by(listOrder); return userService.findAllSort(sort); }
請求findAllMoreSort?sorts=asc,desc¶s=age,name
,對age升序,對name降序,結果如下:
[{ "id": 22, "name": "cc", "age": 11 }, { "id": 20, "name": "aa", "age": 11 }, { "id": 21, "name": "bb", "age": 12 }]
控制臺輸出如下:
Hibernate: select user0_.id as id1_0_, user0_.age as age2_0_, user0_.name as name3_0_ from user user0_ order by user0_.age asc, user0_.name desc
總結
find 相當於增刪改查中的查,也是其中最復雜的一個操作,因為涉及的東西比較多。這篇主要是整理瞭單表的單條查詢和多條查詢,下一篇準備看看單表的分頁查詢。
以上就是Spring JPA find單表查詢方法示例詳解的詳細內容,更多關於Spring JPA find單表查詢的資料請關註WalkonNet其它相關文章!
推薦閱讀:
- 使用Spring Data Jpa查詢全部並排序
- JPA findById方法和getOne方法的區別說明
- SpringBoot JPA sort多屬性排序實例
- Spring JPA學習之delete方法示例詳解
- 全面解析JPA 倉庫repository中的findAll()方法