Flask消息閃現

Flask消息閃現

一個好的應用和用戶界面都需要良好的反饋。如果用戶得不到足夠的反饋,那麼應用最終會被用戶唾棄。

Flask 的閃現系統提供了一個良好的反饋方式。

閃現系統的基本工作方式是:

  • 在且只在下一個請求中訪問上一個請求結束時記錄的消息。
  • 一般我們 結合佈局模板來使用閃現系統。
  • 注意,瀏覽器會限制 cookie 的大小,有時候網絡服 務器也會。這樣如果消息比會話 cookie 大的話,那麼會導致消息閃現靜默失敗。

簡單的例子

以下是一個完整的示例:

from flask import Flask, flash, redirect, render_template, \
     request, url_for

app = Flask(__name__)
app.secret_key = b'_5#y2L"F4Q8z\n\xec]/'

@app.route('/')
def index():
    return render_template('index.html')

@app.route('/login', methods=['GET', 'POST'])
def login():
    error = None
    if request.method == 'POST':
        if request.form['username'] != 'admin' or \
           request.form['password'] != 'secret':
            error = 'Invalid credentials'
        else:
            flash('You were successfully logged in')
            return redirect(url_for('index'))
    return render_template('login.html', error=error)

上面py文件比如保存爲flashtest.py

以下是實現閃現的 layout.html 模板:

注,html模板默認放在項目的templates目錄下。

<!doctype html>
<title>My Application</title>
{% with messages = get_flashed_messages() %}
  {% if messages %}
    <ul class=flashes>
    {% for message in messages %}
      <li>{{ message }}</li>
    {% endfor %}
    </ul>
  {% endif %}
{% endwith %}
{% block body %}{% endblock %}

以下是繼承自 layout.htmlindex.html 模板:

{% extends "layout.html" %}
{% block body %}
  <h1>Overview</h1>
  <p>Do you want to <a href="{{ url_for('login') }}">log in?</a>
{% endblock %}

以下是同樣繼承自 layout.htmllogin.html 模板:

{% extends "layout.html" %}
{% block body %}
  <h1>Login</h1>
  {% if error %}
    <p class=error><strong>Error:</strong> {{ error }}
  {% endif %}
  <form method=post>
    <dl>
      <dt>Username:
      <dd><input type=text name=username value="{{
          request.form.username }}">
      <dt>Password:
      <dd><input type=password name=password>
    </dl>
    <p><input type=submit value=Login>
  </form>
{% endblock %}

運行應用

>set FLASK_APP=flashtest.py
>python -m flask run

訪問默認的127.0.0.1:5000可見閃現效果:

flask_flash

閃現消息的類別

閃現消息還可以指定類別,如果沒有指定,那麼缺省的類別爲 'message' 。不同的 類別可以給用戶提供更好的反饋。例如錯誤消息可以使用紅色背景。(樣式要自己根據class=類別額外去寫好css)

使用 flash() 函數可以指定消息的類別:

flash(u'Invalid password provided', 'error')

注: 這一行是添加在 error= 'Invalid credentials' 這一行之後:

@app.route('/login', methods=['GET','POST'])
def login():
    error = None
    if request.method == 'POST':
        if request.form['username'] != 'admin' or \
           request.form['password'] != 'secret':
            error= 'Invalid credentials'
            flash(u'Invalid password provided', category='error')
        else:
            flash('You were successfully logged in')
            return redirect(url_for('index'))
    return render_template('login.html',error=error)

模板中的 get_flashed_messages() 函數也應當返回類別,顯示消息的循環 也要略作改變:

{% with messages = get_flashed_messages(with_categories=true) %}
  {% if messages %}
    <ul class=flashes>
    {% for category, message in messages %}
      <li class="{{ category }}">{{ message }}</li>
    {% endfor %}
    </ul>
  {% endif %}
{% endwith %}

上例展示如何根據類別渲染消息,還可以給消息加上前綴,如 <strong>{{ category }}:</strong>

<!DOCTYPE html>
<title>My Application</title>
{% with messages = get_flashed_messages(with_categories=True) %}
  {% if messages %}
    <ul class=flashes>
    {% for category, message in messages %}
      <li class="{{ category }}"><strong>{{ category }}:</strong>{{ message }}</li>
    {% endfor %}
    </ul>
  {% endif %}
{% endwith %}
{% block body %}{% endblock %}

注:雖然可以拿到類別,但是要依據類別來寫li標籤的樣式,讓錯誤信息顯示是紅色背景還要自己額外去寫好樣式哦。

過濾閃現消息

你可以視情況通過傳遞一個類別列表來過濾 get_flashed_messages() 的 結果。這個功能有助於在不同位置顯示不同類別的消息。

{% with errors = get_flashed_messages(category_filter=["error"]) %}
{% if errors %}
<div class="alert-message block-message error">
  <a class="close" href="#">×</a>
  <ul>
    {% for msg in errors %}
    <li>{{ msg }}</li>
    {% endfor %}
  </ul>
</div>
{% endif %}
{% endwith %}

flask.flash()get_flashed_messages() 官網說明如下:

Message Flashing

  • flask.flash(message, category='message')

    Flashes a message to the next request. In order to remove the flashed message from the session and to display it to the user, the template has to call get_flashed_messages().

    Parameters:

    message – the message to be flashed.

    category – the category for the message.

    The following values are recommended:

    'message' for any kind of message,

    'error' for errors,

    'info' for information messages and 'warning' for warnings.

    However any kind of string can be used as category.

  • flask.get_flashed_messages(with_categories=False, category_filter=[])

    Pulls all flashed messages from the session and returns them. Further calls in the same request to the function will return the same messages. By default just the messages are returned, but when with_categories is set to True, the return value will be a list of tuples in the form (category, message) instead. Filter the flashed messages to one or more categories by providing those categories in category_filter. This allows rendering categories in separate html blocks. The with_categories and category_filter arguments are distinct: with_categories controls whether categories are returned with message text (True gives a tuple, where False gives just the message text). category_filter filters the messages down to only those matching the provided categories.

    See 消息閃現 for examples.

    Parameters:

    with_categories – set to True to also receive categories.

    category_filter – whitelist of categories to limit return values

從官網裏可以看出,flash() 函數:

  • 第一個參數是你將要放進去的字符串消息,

  • 第二個默認參數category,代表消息的類別,默認爲message(消息,普通)。

get_flashed_messages() 兩個默認參數,第一個是類別控制開關,默認是False。

  • 類別控制是否帶消息文本返回類別:
    • True給出一個tuple,元祖中給出兩個值,分別是消息文本和類別;
    • False只給出消息文本,不返回類別。

文:鐵樂與貓

2018-9-6

參考

Flask-消息隊列

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章