zoukankan      html  css  js  c++  java
  • Flask学习之旅--分页功能:分别使用 flask--pagination 和分页插件 layPage

    一、前言

      现在开发一个网站,分页是一个很常见的功能了,尤其是当数据达到一定量的时候,如果都显示在页面上,会造成页面过长而影响用户体验,除此之外,还可能出现加载过慢等问题。因此,分页就很有必要了。

      分页功能的常用的实现方法有两种:前台分页和后台分页。前台分页就是一次查询取出所有数据保存在内存中,需要的时候就从相应区间中取数据,但只适用于少量数据的情况。后台分页就是查询时只取出相应区间中的数据并返回,翻页时再次查询并取数据,此方法能减小传输压力提高性能。今天这篇博客就记录一下在 Flask 中怎么使用 Flask 的扩展库 flask-pagination 和分页插件 layPage 实现分页功能。

    二、准备工作

    1.Flask 环境配置

      首先你需要一个 Python 环境,然后需要安装几个第三方库:

    • flask
    • pymysql
    • flask-pagination
    • SQLAlchemy

      使用如下命令进行安装:

    pip install flask

    pip install pymysql

    pip install flask-pagination

    pip install SQLAlchemy

    2.layui 下载安装

      layui 是一个经典模块化前端 UI 框架,网址为:https://www.layui.com/,也可以直接点击这里进行下载。

      layui 是一款采用自身模块规范编写的前端 UI 框架,遵循原生 HTML/CSS/JS 的书写与组织形式,门槛极低,拿来即用。其外在极简,却又不失饱满的内在,体积轻盈,组件丰盈,从核心代码到 API 的每一处细节都经过精心雕琢,非常适合界面的快速开发。

      

    3.数据准备

      这次使用的数据库是 MySQL,建了一个表 students,这个表只有两个字段:stu_id 和 stu_name,表中数据如下:

      

    三、使用flask-pagination

       要使用 flask-pagination 来进行分页,需要从中导出一个类 Pagination:

    from flask_paginate import Pagination

      下面是分页的代码:

     1 @app.route('/index')
     2 def index(limit=10):
     3     sess = DBSession()
     4     data = sess.query(t_students).all()
     5     page = int(request.args.get("page", 1))
     6     start = (page - 1) * limit
     7     end = page * limit if len(data) > page * limit else len(data)
     8     paginate = Pagination(page=page, total=len(data))
     9     ret = sess.query(t_students).slice(start, end)
    10     return render_template("index.html", data=ret, paginate=paginate)

       其中 limit 表示每页显示的条数,page 代表页数,start 和 end 分别表示该页面显示的数据区间,然后实例化 Pagination 类。这里我只传入了两个参数:page 和 total(total 代表数据总条数),除了这两个参数,还可以传入其他参数,例如:

    • bs_version:支持的 BootStrap 版本,默认为2;
    • css_framework:使用的 CSS 框架,默认为 BootStrap;
    • url_coding:URL 编码格式,默认为 UTF-8。

      在代码中,我使用了 render_template 来渲染页面并返回数据,下面是前端中的核心代码:

     1 <table>
     2 <thead>
     3     <tr>
     4         <th>ID</th>
     5         <th>NAME</th>
     6     </tr>
     7     </thead>
     8     <tbody>
     9     {% for i in data %}
    10         <tr>
    11             <td>{{ i.stu_id }}</td>
    12             <td>{{ i.stu_name }}</td>
    13         </tr>
    14     {% endfor %}
    15     </tbody>
    16 </table>
    17 {{ paginate.links }}

      最终得到的结果如下:

      

    四、使用layPage

      可以看到使用 flask-pagination 得到的分页效果是比较简单的,但如果想要更好的效果,可以使用一些前端框架来实现,例如 layui 中的分页插件 layPage。layPage 致力于提供极致的分页逻辑,既可轻松胜任异步分页,也可作为页面刷新式分页,可以在这里查看文档。

      首先需要导入 layui.js 和 layui.css:

    <script src="../static/layui.js"></script>
    <link rel="stylesheet" href="../static/css/layui.css">

      laypage 的使用非常简单,指向一个用于存放分页的容器,通过服务端得到一些初始值,即可完成分页渲染。例如:

     1 <div>
     2     <table>
     3         <thead>
     4         <tr>
     5             <th></th>
     6             <th>ID</th>
     7             <th>NAME</th>
     8         </tr>
     9         </thead>
    10         <tbody id="demoBody"></tbody>
    11     </table>
    12     <div id="demo"></div>
    13 </div>
    View Code

      其中 demo 用于存放分页,demoBody 则用于显示数据内容。但要实现分页,还需要使用 laypage.render() 来渲染。在 laypage.render() 中,有一些核心参数:

    • elem:指向存放分页的容器,可以是 ID、DOM 对象;
    • count:数据总量,一般通过服务端得到;
    • limit:每页显示条数,默认为10条;
    • prev:自定义“上一页”的内容,支持传入普通文本和HTML;
    • next:自定义“下一页”的内容,支持传入普通文本和HTML;
    • theme:自定义主题,支持传入颜色值或任意普通字符。

      这里使用 layPage 来显示分页内容,而具体数据内容则需要使用 JS 来加载,具体代码如下:

     1 <script>
     2     $(function () {
     3         initPage();
     4     });
     5 
     6     function initPage(pageConf) {
     7         if (!pageConf) {
     8             pageConf = {};
     9             pageConf.pageSize = 10;
    10             pageConf.currentPage = 1;
    11         }
    12         $.post("http://127.0.0.1:5000/get_data", pageConf, function (data) {
    13             layui.use(['laypage', 'layer'], function () {
    14                 var page = layui.laypage;
    15                 page.render({
    16                     elem: 'demo',
    17                     count: data.count,
    18                     curr: pageConf.currentPage,
    19                     limit: pageConf.pageSize,
    20                     first: "首页",
    21                     last: "尾页",
    22                     layout: ['count', 'prev', 'page', 'next', 'limit', 'skip'],
    23                     jump: function (obj, first) {
    24                         if (!first) {
    25                             pageConf.currentPage = obj.curr;
    26                             pageConf.pageSize = obj.limit;
    27                             initPage(pageConf);
    28                         }
    29                     }
    30                 });
    31                 fillTable(data["data"], (pageConf.currentPage - 1) * pageConf.pageSize); //页面填充
    32             })
    33         });
    34     }
    35 
    36     //填充表格数据
    37     function fillTable(data, num) {
    38         $("#demoBody").html('');
    39         $.each(data, function (index, obj) {
    40             // id 很多时候并不是连续的,如果为了显示比较连续的记录数,可以这样根据当前页和每页条数动态的计算记录序号
    41             index = index + num + 1;
    42             var info = '';
    43             info += '<tr>';
    44             info += '<td>' + index + '</td>';
    45             info += '<td>' + obj.id + '</td>';
    46             info += '<td>' + obj.name + '</td>';
    47             info += '</tr>';
    48             $("#demoBody").append(info);
    49         });
    50     }
    51 </script>
    View Code

      前端代码完成了,还需要一个提供数据的接口,可以使用 Flask 定义一个路由来实现,例如:

     1 @app.route('/get_data', methods=['POST'])
     2 def get_data():
     3     sess = DBSession()
     4     data = sess.query(t_students).all()
     5     limit = int(request.form.get("pageSize"))
     6     page = int(request.form.get("currentPage"))
     7     start = (page - 1) * limit
     8     end = page * limit if len(data) > page * limit else len(data)
     9     ret = [{"id": data[i].stu_id, "name": data[i].stu_name} for i in range(start, end)]
    10     return {"data": ret, "count": len(data)}

      前端使用了 POST 请求,传输的数据包括当前页数和每页显示条数,然后在 Flask 中使用 request.form.get() 来获取数据,得到页数和条数后取出相应区间中的数据,返回的结果是一个 JSON 格式数据,其中 data 表示数据,count 表示数据总条数。

      最终得到的结果如下:

      

      完整代码已上传到 GitHub

  • 相关阅读:
    Live2d Test Env
    Live2d Test Env
    Live2d Test Env
    Live2d Test Env
    Live2d Test Env
    Live2d Test Env
    Live2d Test Env
    Live2d Test Env
    python嵌套列表知多少
    旋转图像
  • 原文地址:https://www.cnblogs.com/TM0831/p/12087966.html
Copyright © 2011-2022 走看看