分页处理 - 若依cloud -【 129 】

129 分页功能实现详解 | RuoYi

  • 前端采用基于bootstrap的轻量级表格插件bootstrap-table(opens new window)
  • 后端采用基于mybatis的轻量级分页插件pageHelper(opens new window)

提示:

        前后端分页实现流程

一 前端

1 element-ui提供了el-pagination,可以直接去使用,是没问题的。

2 只是说项目里也封装了一个pagination组件,src\components\Pagination\index.vue。封装后的pagination组件兼容el-pagination,即el-pagination的所有属性、事件等等都会被支持。






3 全局注册封装的pagination组件(在前端任何页面都可以使用):main.js

// 全局组件挂载
Vue.component('Pagination', Pagination)
// 分页组件
import Pagination from "@/components/Pagination";

4 封装的pagination组件的使用案例:src\views\system\role\selectUser.vue

5 前端调用实现:前端定义分页流程

// 一般在查询参数中定义分页变量
queryParams: {
  pageNum: 1,
  pageSize: 10
},

// 页面添加分页组件,传入分页变量


// 声明分页参数和查询参数
export default {
  data() {
    return {
      // 查询参数
      queryParams: {
        pageNum: 1,            // 第1页
        pageSize: 10,          // 每页10条
        roleId: undefined,     // 查询条件1:roleId,角色id
        userName: undefined,   // 查询条件2:用户名称 
        phonenumber: undefined // 查询条件3:电话号码
      }
    };
  }
}

// 调用后台方法,传入参数 获取结果
// queryParams是分页参数和查询参数
listUser(this.queryParams).then(response => {
    this.userList = response.rows;
    this.total = response.total;
  }
);

​​​​6 扩展:一般在项目里直接用封装的分页组件就已经足够满足了。如果不满足的话,可以再参考el-pagination去定制一些属性加进来。或者是你直接用饿了么的也可以啊,都是可以的。 

二 后端

1 ruoyi-common-core#TableDataInfo:表格分页数据对象,其中rows就是表格数据

public class TableDataInfo implements Serializable
{
    private static final long serialVersionUID = 1L;

    /** 总记录数 */
    private long total;

    /** 列表数据 */
    private List rows;

    /** 消息状态码 */
    private int code;

    /** 消息内容 */
    private String msg;
}

2 ruoyi-common-core#PageUtils:解决实体类(如下面的SysPost sysPost)中都没有pageSize和pageNumber属性接收前端参数

/**
 * 分页工具类
 * 
 * @author ruoyi
 */
public class PageUtils extends PageHelper
{
    /**
     * 设置请求分页数据:
     *      就是从request中把前端传过来的几个参数拿过来。
     *      然后设置到pageDomain里面。
     */
    public static void startPage()
    {
        PageDomain pageDomain = TableSupport.buildPageRequest();
        Integer pageNum = pageDomain.getPageNum();
        Integer pageSize = pageDomain.getPageSize();
        String orderBy = SqlUtil.escapeOrderBySql(pageDomain.getOrderBy());
        Boolean reasonable = pageDomain.getReasonable();
        // 调用分页插件
        PageHelper.startPage(pageNum, pageSize, orderBy).setReasonable(reasonable);
    }
}

3 ruoyi-system#SysPostController#list

    /**
     * 获取岗位列表
     */
    @RequiresPermissions("system:post:list")
    @GetMapping("/list")
    public TableDataInfo list(SysPost post)
    {
        // 分页
        startPage();
        // 当前页数据
        List list = postService.selectPostList(post);
        // 返回给前端
        return getDataTable(list);
    }

4 【pagehelper框架】PageMethod#startPage:分页

    // 当前请求
    protected static final ThreadLocal LOCAL_PAGE = new ThreadLocal();

    // 即在当前请求下面,去给我们进行一个分页
    // 会自动在sql语句中拼接pageNum、pageSize、orderBy这3个参数的limit分页语句
    // 简化代码:不用在SysPostMapper.xml中修改sql语句
    public static  Page startPage(int pageNum, int pageSize, String orderBy) {
        Page page = startPage(pageNum, pageSize);
        page.setOrderBy(orderBy);
        return page;
    }

5 扩展:如果不想分页,就把startPage();这句代码删掉就行了。

三 注意事项(坑)

1 常见坑点1:selectPostById莫名其妙的分页。例如下面这段代码

startPage();
List list;
if(user != null){
    list = userService.selectUserList(user);
} else {
    list = new ArrayList();
}
// 当user == null时,分页会消费在此查询上。
// 本来是查询单个的,但结果却莫名其妙给你分了个页
Post post = postService.selectPostById(1L);
return getDataTable(list);

原因分析:这种情况下由于user存在null的情况,就会导致pageHelper生产了一个分页参数,但是没有被消费,这个参数就会一直保留在这个线程上。 当这个线程再次被使用时,就可能导致不该分页的方法去消费这个分页参数,这就产生了莫名其妙的分页。
上面这个代码,应该写成下面这个样子才能保证安全。

        就是说你使用了这个startPage,你又不去分页啊,这个地方又没有分页。那么的话,你下一次查询就是下一个查询,它就会带上这个分页,所以的话呢就会莫名其妙。这个你本来不需要分页的,反而被分页了,所以的话就需要注意一下。

List list;
if(user != null){
	startPage();
	list = userService.selectUserList(user);
} else {
	list = new ArrayList();
}
Post post = postService.selectPostById(1L);
return getDataTable(list);

2 常见坑点2:添加了startPage方法。也没有正常分页。例如下面这段代码

startPage();
// 错:分页错误地加上这里
Post post = postService.selectPostById(1L);
List list = userService.selectUserList(user);
return getDataTable(list);

原因分析:只对该语句以后的第一个查询(Select)语句得到的数据进行分页。
上面这个代码,应该写成下面这个样子才能正常分页。

        因为的话,你下面的话必须是你分页的那个sql语句的一个查询方法(XxxMapper.xml)。

Post post = postService.selectPostById(1L);
startPage();
List list = userService.selectUserList(user);
return getDataTable(list);

3 提示

        项目分页插件默认是Mysql语法,如果项目改为其他数据库需修改配置application.yml文件中的属性helperDialect: 你的数据库

4 注意

        只要你可以保证在PageHelper方法调用后紧跟MyBatis查询方法,这就是安全的。因为PageHelperfinally代码段中自动清除了ThreadLocal存储的对象。 如果代码在进入Executor前发生异常,就会导致线程不可用,这属于人为的Bug(例如接口方法和XML中的不匹配,导致找不到MappedStatement时),这种情况由于线程不可用,也不会导致ThreadLocal参数被错误的使用。

你可能感兴趣的:(vue.js,前端,javascript)