我是靠谱客的博主 粗犷烧鹅,最近开发中收集的这篇文章主要介绍微服务12-分页查询分页查询,觉得挺不错的,现在分享给大家,希望可以做个参考。

概述

目录

分页查询

分页查询的优点

PageHelper实现分页查询

PageHelper的基本使用

先编写持久层

编写业务逻辑层

编写控制层

使用JsonPage返回结果


分页查询

分页查询的优点

所谓分页,就是查询结果数据较多时,采用按页显示的方法,而不是一次性全部显示

分页的优点:

  1. 服务器:一次性查询所有信息,服务器压力大,分页查询服务器压力小
  2. 客户端:一次性显示所有信息,需要更多流量,加载时间也会更长,分页显示没有这个问题
  3. 用户体验上:一般最有价值的信息都会在前几页显示,也方便用户记忆,多查询出来的数据使用几率很低

实现分页查询需要我们开发过程中多几个步骤

PageHelper实现分页查询

我们可以使用sql语句中添加limit关键字的方法实现分页查询

但是查询分页内容时,我们要自己计算相关的分页信息和参数

limit 0,10 limit 10,10

分页逻辑无论什么业务都是类似的,所以有框架帮助我们高效实现分页功能

PageHelper框架可以实现我们提供页码和每页条数,自动实现分页效果,收集分页信息

PageHelper的分页原理就是在程序运行时,在sql语句尾部添加limit关键字,并按照分页信息向limit后追加分页数据

要想使用,首先还是添加依赖

我们在之前搭建的微服务项目中先编写学习,建议使用csmall-order模块

<dependency>
    <groupId>com.github.pagehelper</groupId>
    <artifactId>pagehelper-spring-boot-starter</artifactId>
</dependency>

在添加seata支持时已经添加了pagehepler依赖

PageHelper的基本使用

先编写持久层

我们使用csmall-order-webapi模块来完成分页的测试

首先编写分页的持久层mapper,持久层功能是全查所有订单信息

OrderMapper添加方法

// pageHelper框架完成分页功能的原理是sql语句后自动添加limit
// 所以在编写查询方法时,和普通查询没有任何区别
@Select("select id,user_id,commodity_code,count,money from order_tbl")
List<Order> findAllOrders();

注意这个方法并不需要任何分页的参数或返回值,sql也不需要编写limit

都是在业务逻辑层中由PageHelper框架处理的

编写业务逻辑层

下面就转到业务逻辑层实现类,先编写一个方法使用PageHelper的功能

先不用写接口,直接在业务逻辑层中写方法

OrderServiceImpl添加方法

// 分页查询所有订单信息的方法
// page是页码,pageSize是每页条数
public PageInfo<Order> getAllOrdersByPage(Integer page,Integer pageSize){
    // PageHelper框架实现分页功能最核心的代码要编写在执行查询的代码之前
    // 使用指定的代码设置要查询的页码和每页的条数
    // 在后面执行查询时,会自动按照这里指定的数据执行分页查询
    // page是页码,1就是查询第一页,pageSize是每页条数
    PageHelper.startPage(page,pageSize);
    // 下面执行查询操作,这个操作会被PageHelper框架在运行的sql语句末尾添加limit语句
    List<Order> list= orderMapper.findAllOrders();

    // list中的数据就是按照分页条件查询出来的某一页的数据
    // 但是分页查询方法返回的并不是list类型的对象,我们也需要获得分页的信息
    // 然后将查询出的数据和分页信息结合返回,这个类型,就是PageInfo
    
    return new PageInfo<>(list);
    
}

PageInfo对象既包含查询数据结果,又包含分页信息

数据结构如下图

附:PageInfo全部分页信息属性

//当前页
private int pageNum;
//每页的数量
private int pageSize;
//当前页的行数量
private int size;
//当前页面第一个元素在数据库中的行号
private int startRow;
//当前页面最后一个元素在数据库中的行号
private int endRow;
//总页数
private int pages;
//前一页页号
private int prePage;
//下一页页号
private int nextPage;
//是否为第一页
private boolean isFirstPage;
//是否为最后一页
private boolean isLastPage;
//是否有前一页
private boolean hasPreviousPage;
//是否有下一页
private boolean hasNextPage;
//导航条中页码个数
private int navigatePages;
//所有导航条中显示的页号
private int[] navigatepageNums;
//导航条上的第一页页号
private int navigateFirstPage;
//导航条上的最后一页号
private int navigateLastPage;

编写控制层

@GetMapping("/page")
@ApiOperation("分页查询所有订单")
@ApiImplicitParams({
        @ApiImplicitParam(value = "页码",name="page",example = "1"),
        @ApiImplicitParam(value = "每页条数",name="pageSize",example = "8")
})
public JsonResult<PageInfo<Order>> pageOrders(
                                Integer page,Integer pageSize){
    PageInfo<Order> pageInfo=orderService.getAllOrdersByPage(page,pageSize);
    return JsonResult.ok("查询完成",pageInfo);
}

启动NacosSeata

启动order

进行knife4j测试http://localhost:20002/doc.html#/home

可以观察控制台输出的运行的sql语句(会自动添加limit关键字)

使用JsonPage返回结果

当前我们分页查询返回的类型是PageInfo

如果用这个类型来做业务逻辑层的返回值,当当前方法作为dubbo生产者对外提供服务时

消费者调用该服务需要使用PageInfo类型对象来接收,这样要求消费者也添加PageHepler依赖,这是不合理的

所以我们设计在commons模块中,添加一个专门用于返回分页结果的类JsonPage,代替PageInfo

这样当前微服务项目中,所有分页或类似的操作,就都可以使用这个类了

例如之前SpringDataElasticsearch框架也支持分页,返回类型为Page,它也可以替换为JsonPage

因为需要在commons模块中使用PageInfo类型,所以commons模块要添加pageHelper的依赖

<!--   为了将PageHelper框架中分页查询结果返回值PageInfo转换成JsonPage类型的依赖   -->
<dependency>
    <groupId>com.github.pagehelper</groupId>
    <artifactId>pagehelper</artifactId>
    <version>5.2.0</version>
</dependency>

在restful包中新建一个JsonPage类

代码如下

@Data
public class JsonPage<T> implements Serializable {

    // 根据实际需求,定义需要的分页信息
    // 这里暂时只声明最基本的4个分页信息,如果有需求变化,随时添加即可
    @ApiModelProperty(value = "总页数",name="totalPages")
    private Integer totalPages;
    @ApiModelProperty(value = "总条数",name="totalCount")
    private Long totalCount;
    @ApiModelProperty(value = "当前页码",name="page")
    private Integer page;
    @ApiModelProperty(value = "每页条数",name="pageSize")
    private Integer pageSize;

    // JsonPage除了包含分页信息之外,也要包含查询到的数据
    @ApiModelProperty(value = "分页数据",name="list")
    private List<T> list;


    // 上面定义了所有分页需要的属性
    // 下面编写一个将PageInfo类型转换为JsonPage类型的方法
    // 如果需要转换别的类型(例如SpringData分页Page类型),编写一个新的方法即可
    public static <T> JsonPage<T>  restPage(PageInfo<T> pageInfo){
        // 所谓的转换就是将参数pageInfo中的信息,赋值到JsonPage对应的属性中
        JsonPage<T> result=new JsonPage<>();
        // 先赋值分页信息
        result.setTotalPages(pageInfo.getPages());
        result.setTotalCount(pageInfo.getTotal());
        result.setPage(pageInfo.getPageNum());
        result.setPageSize(pageInfo.getPageSize());
        // 再赋值分页数据
        result.setList(pageInfo.getList());
        // 最后返回赋完值的jsonPage对象
        return result;
    }

}

下面去使用这个类

csmall-order-service业务逻辑层接口项目添加方法

返回值使用JsonPage

// 返回JsonPage类型的分页查询全部订单方法
JsonPage<Order> getAllOrdersByPage(Integer page,Integer pageSize);

csmall-order-webapi项目实现类中进行修改

//     ↓↓↓↓↓↓↓↓
public JsonPage<OrderTb> getAllOrdersByPage(Integer pageNum, Integer pageSize){

    PageHelper.startPage(pageNum,pageSize);

    List<OrderTb> list= orderMapper.findAllOrders();

    //     ↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓
    return JsonPage.restPage(new PageInfo<>(list));
}

业务逻辑层返回值的修改影响控制器方法的调用

再去修改OrderController中方法调用的位置

@Autowired
//      ↓↓↓↓↓↓↓↓↓↓↓↓
private IOrderService orderService;

//...
//                ↓↓↓↓↓↓↓↓
public JsonResult<JsonPage<Order>> pageOrders(Integer pageNum, Integer pageSize){
      // 分页调用
      //↓↓↓↓↓↓        ↓↓↓↓↓↓↓↓↓  
      JsonPage<Order> jsonPage=orderService.getAllOrdersByPage(
          pageNum,pageSize);
      //                            ↓↓↓↓↓↓↓↓↓↓
      return JsonResult.ok("查询完成",jsonPage);
}

保证启动NacosSeata

重启order测试

能出现查询结果即可

最后

以上就是粗犷烧鹅为你收集整理的微服务12-分页查询分页查询的全部内容,希望文章能够帮你解决微服务12-分页查询分页查询所遇到的程序开发问题。

如果觉得靠谱客网站的内容还不错,欢迎将靠谱客网站推荐给程序员好友。

本图文内容来源于网友提供,作为学习参考使用,或来自网络收集整理,版权属于原作者所有。
点赞(36)

评论列表共有 0 条评论

立即
投稿
返回
顶部