从 Flask 中的 html 模板排序查询数据

Ordering query data from html template in flask

我正在使用时间对查询结果进行排序,但我想让用户能够选择他想要的数据排序方式,假设他想使用字母顺序或者他想按升序或降序排序我想知道如何在烧瓶中使用它,抱歉我的英语不好

这是我的代码

@routes.route('/posts')
def show_posts():
    page=request.args.get('page',1,type=int)
    posts=Posts.query.order_by(Posts.timestamp.desc).paginate(page,per_page=10)
    return render_template('routes/show_posts.html',posts=posts)

好的,这是我的第一个 flask 答案(我昨天才完成教程):

EDIT/INFO:最后我没有用任何表格来完成,只是简单的路线,但表格也可以使用,这看起来更简单一点(更多是因为我不会弄清楚如何为此使用这些表格:))

EDIT2/INFO:我也不认为对于这个特定的代码,装饰器中的 methods 参数没有任何必要,因此对于这个特定的代码

可能会被删除

主文件(它包含所有内容,因为这比显示我会使用的每个模块更容易)

from flask import Flask, render_template, url_for
from flask_sqlalchemy import SQLAlchemy


app = Flask(__name__)
app.config['SQLALCHEMY_DATABASE_URI'] = 'sqlite:///site.db'

db = SQLAlchemy(app)


class Post(db.Model):
    id = db.Column(db.Integer, primary_key=True)
    title = db.Column(db.String(100), nullable=False)
    content = db.Column(db.Text, nullable=False)


@app.route('/posts/filter_by/<string:key>')
@app.route('/posts', methods=['GET', 'POST'])
@app.route('/')
def all_posts(key=None):
    posts = Post.query.order_by(Post.title.asc()).all()
    if key == 'ZA':
        posts = Post.query.order_by(Post.title.desc()).all()
    return render_template('posts.html', posts=posts)


if __name__ == '__main__':
    app.run(debug=True)

这是模板(使用 bootstrap 东西):

<!doctype html>
<html lang="en">
  <head>
    <!-- Required meta tags -->
    <meta charset="utf-8">
    <meta name="viewport" content="width=device-width, initial-scale=1, shrink-to-fit=no">

    <!-- Bootstrap CSS -->
    <link rel="stylesheet" href="https://stackpath.bootstrapcdn.com/bootstrap/4.3.1/css/bootstrap.min.css" integrity="sha384-ggOyR0iXCbMQv3Xipma34MD+dH/1fQ784/j6cY/iJTQUOhcWr7x9JvoRxT2MZw1T" crossorigin="anonymous">

    <title>Hello, world!</title>
  </head>
  <body>

    <div class="dropdown">
      <button class="btn btn-secondary dropdown-toggle"
              type="button" id="dropdownMenu1" data-toggle="dropdown"
              aria-haspopup="true" aria-expanded="false">
        Sort by
      </button>
      <div class="dropdown-menu" aria-labelledby="dropdownMenu1">
        <a class="dropdown-item" href="{{ url_for('all_posts', key='AZ') }}">A-Z</a>
        <a class="dropdown-item" href="{{ url_for('all_posts', key='ZA') }}">Z-A</a>
      </div>
    </div>

    {% for post in posts %}
        <div class="card">
            <div class="card-body">
                <h4 class="card-title">{{ post.title }}</h4>
                <p class="card-text">{{ post.content }}</p>
            </div>
        </div>
    {% endfor %}

    <!-- Optional JavaScript -->
    <!-- jQuery first, then Popper.js, then Bootstrap JS -->
    <script src="https://code.jquery.com/jquery-3.3.1.slim.min.js" integrity="sha384-q8i/X+965DzO0rT7abK41JStQIAqVgRVzpbzo5smXKp4YfRvH+8abtTE1Pi6jizo" crossorigin="anonymous"></script>
    <script src="https://cdnjs.cloudflare.com/ajax/libs/popper.js/1.14.7/umd/popper.min.js" integrity="sha384-UO2eT0CpHqdSJQ6hJty5KVphtPhzWj9WO1clHTMGa3JDZwrnQq4sF86dIHNDz0W1" crossorigin="anonymous"></script>
    <script src="https://stackpath.bootstrapcdn.com/bootstrap/4.3.1/js/bootstrap.min.js" integrity="sha384-JjSmVgyd0p3pXB1rRibZUAYoIIy6OrQ6VrjIEaFf/nJGzIxFDsf4x0xIM+B07jRM" crossorigin="anonymous"></script>
  </body>
</html>

所以第一件事(自上而下):

导入所有需要的东西
然后初始化 Flask 和 SQLAlchemy 类 并将应用程序配置到数据库

创建 post 模型来存储 post 和东西(我不太清楚)

接下来是主要部分——路线。

所以我首先创建一个带有变量的路由:

@app.route('/posts/filter_by/<string:key>')

这将允许请求此 URL 并能够(从该变量)获取有助于处理响应的其他信息

然后添加更多路线,使 url 看起来更干净,这几乎是唯一的原因(据我所知)

然后定义函数:
将其命名为您喜欢的名称,但您必须将变量作为参数传递,并且由于使用了多个路由,并且可能出于其他原因也为该参数设置了默认值,因此不必提供它

然后使用简单的 if 语句并使用该变量处理 post 的排序方式

然后 return 模板按顺序包含那些 post

现在关于模板

首先它使用 bootstrap 东西,我从那里获得了最多的代码(只需从他们的网站复制粘贴)或 here 这是一个很好的备忘单。

所以我从备忘单中复制了下拉菜单并更改了一些值,最显着的是 href 属性:

那些我用 url_for 函数替换并也传递了变量,如您所见,发送的请求使用该变量,该变量将允许处理 post 的排序方式

希望一切都清楚,如果您还有其他问题,请提出。

首先,Matiiss,您的回答非常好,感谢您的帮助,现在我找到了另一种方法,它与 Matiiss 的回答有一些相似之处,我想分享它,所以如果有人发现这个问题,现在您有两个答案可供选择来自.

@routes.route('/posts')
def show_posts():
    posts= Posts.query.order_by(Posts.name.desc()).all()
    filter_rule = request.args.get('filter')
    if filter_rule == 'A-Z':
        posts= Posts.query.order_by(Posts.name).all()
    return render_template('posts.html',posts=posts)

HTML部分

<div class="row">
        <div class="col-md-3">
            <div class="nav nav-pills flex-column" role="tablist" aria-orientation="vertical">
                <a class="nav-item nav-link"
                   href="{{ url_for('.show_posts', filter='A-Z') }}">
                    A-Z
                </a>
                <a class="nav-item nav-link"
                   href="{{ url_for('.show_posts', filter='Z-A') }}">
                    Z-A
                </a>
            </div>
        </div>