在模板中渲染錯誤消息
如果form.valicate_on_submit()返回False,說明驗證沒有通過,對於沒有驗證通過的字段,WTForms會把錯誤信息添加到表單類的errors屬性中,這是一個匹配作為表單字段的類屬性到對應的錯誤消息列表的字典。我們一般會直接通過字段名來獲取對應字段的錯誤消息列表,即”form.字段名.errors”。比如,form.name.errors返回name字段的錯誤消息列表。
像渲染flash()消息一樣,我們在模板里用for循環遍歷錯誤消息列表,例如:
basic.html模板:
{% extends 'base.html' %} {% block content %} <form method="post"> {{ form.csrf_token }} {{ form.username.label }}<br> {{ form.username() }}<br> {% for message in form.username.errors %} <small class="error">{{ message }}</small><br> {% endfor %} {{ form.password.label }}<br> {{ form.password }}<br> {% for message in form.password.errors %} <small class="error">{{ message }}</small><br> {% endfor %} {{ form.remember }}{{ form.remember.label }}<br> {{ form.submit }}<br> </form> {% endblock %}
為了讓錯誤消息更加醒目,我們為錯誤消息元素添加了error類,在style.css中定義它的樣式顏色為紅色:
此時訪問,127.0.0.1:5000/basic,如果沒有輸入內容二提交按鈕,會看到瀏覽器內置的錯誤提示,而不是我們程序里想要提示的消息:
使用DataReqired和InputRequired驗證器時,WTForms會在字段輸出的HTML代碼中添加required屬性,所以會彈出瀏覽器內置的錯誤提示。
同時,WTForms也會在表單字段的flags屬性添加required標志,如(form.username.flags.required),所以我們可以在模板中通過這個標志值來判斷是否在字段文本中添加一個*號或文字標注,以表示必填項。
如果在username輸入空格,password里面輸入數值長度小於6,這樣兩個表單字段在驗證validate()的時候,就會觸發如下錯誤提示
InputRequired驗證器和DataRequired很相似,但InputRequired僅驗證用戶是否有輸入,而不管輸入的值是否有效。例如,有空格組成的數據也會通過驗證。當是DataRequired時,如果用戶輸入的數據不符合字段要求,比如在IntegerField輸入非數字時會視為未輸入,而不是類型錯誤。
表單處理流程圖
下面說下完整的表單處理過程的流程,如下圖:
涉及的文件有app.py, form.py, base.html, basic.html, styles.css, hello.html
設置錯誤提示語言:
WTForms內置了多種語言的錯誤消息,如果想改變內置錯誤消息的默認語言,可以通過自定義表單類實現,這個功能要求Flask-WTF版本大於0.14.2或單獨使用WTForms。本人機器上裝的是0.14.2版本,所以下面介紹的功能無法使用,只是做個記錄先。
下面的例子代碼中,創建了一個MyBaseForm基類,所有繼承這個基類的表單類的內置錯誤消息語言都會設為簡體中文。
from flask_wtf import FlaskForm app=Flask(__name__) app.config['WTF_I18N_ENABLED'] = False class MyBaseForm(FlaskForm): class Meta: locales = ['zh'] class HelloForm(MyBaseForm): name = StringField('Name', validators=[DataRequired()]) submit = SubmitField()
首先,我們需要將配置變量WTF_I18N_ENABLED設為False,這會讓Flask-WTF使用WTForms內置的錯誤消息翻譯。然后我們需要在自定義基類中定義Meta類,並在localse列表中加入簡體中文的地區字符串。在創建表單時,繼承這個MyBaseForm即可將錯誤消息語言設為中文,比如上面定義的HelloForm。另外也可以在實例化表單類時通過meta關鍵字傳入locales值,如:
form = MyForm(meta={‘locales’:[‘en_US’, ‘en’]})
才用上面代碼的方式,可以改一下app.py中視圖函數的內容:
@app.route('/basic', methods=['GET', 'POST']) def basic(): form = HelloForm() if form.validate_on_submit(): username = form.name.data flash('Welcom home, %s!' % username) return redirect(url_for('hello')) return render_template('basic.html', form = form)
然后把basic.html里的form部分改一下:
<form method="post"> {{ form.csrf_token }} {{ form.name.label }}<br> {{ form.name() }}<br> {% for message in form.name.errors %} <small class="error">{{ message }}</small><br> {% endfor %} {{ form.submit }}<br> </form>
之后頁面上提交的時候,如果版本符合的話,錯誤消息就會顯示中文,但是我本地環境只能顯示英文。
locales屬性是一個根據優先級排列的地區字符串列表。在WTForms中,簡體中文和繁體中文的地區字符串分別為zh和zh_TW。