开发者

Spring JPA find单表查询方法示例详解

开发者 https://www.devze.com 2023-04-27 10:55 出处:网络 作者: 烟雨戏江南
目录一、findById(ID id)二、findAll()三、findAllById(Iterable<ID> ids)四、findAll(Sort sort) 单调排序sort.by 源码control层五、findAll(Sort sort) 多参数排序Sort by 源码control 层总结一、findById(I
目录
  • 一、findById(ID id)
  • 二、findAll()
  • 三、findAllById(Iterable<ID> ids)
  • 四、findAll(Sort sort) 单调排序
    • sort.by 源码
    • control层
  • 五、findAll(Sort sort) 多参数排序
    • Sort by 源码
    • control 层
  • 总结

    一、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 (metadjavascriptata == 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 user0www.devze.com_.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 us开发者_C开发erService.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.leng编程客栈th > 0, "At least one property must be given");
       return Sort.by(Arrays.stream(properties)//
             .map(it -> new Order(direction, it))//
             .collect(Collectors.toList()));
    }

    可以看到我们需要传入两个参数,分别是 directionproperties

    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&para=age,name,对 agename 进行降序排序,结果如下:

    [{
    	"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> findAjavascriptllMoreSort(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&paras=age,name,对age升序,对name降序,结果如下:

    [{
    	"id": 22,
    	"name": "cc",
    	"age": 11
    }, {
    	"id": 20,
    	"name": "aa",
    	"age": 11
    }, {
    	"id": 21,
    	"n编程ame": "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单表查询的资料请关注我们其它相关文章!

    0

    精彩评论

    暂无评论...
    验证码 换一张
    取 消

    关注公众号