Flask中使用WTForms处理表单验证
在 Flask 中,WTForms
是一个用于 处理表单验证 的库,可以与 Flask 结合,提供表单验证、数据清理、错误提示等功能。
1. 安装 Flask-WTF
首先安装 Flask-WTF
:
pip install Flask-WTF
Flask-WTF
是 WTForms
的 Flask 扩展,提供了 CSRF 保护 和 Flask 兼容的表单处理。
2. 基本使用
(1) 创建 Flask 应用
from flask import Flask, render_template, request, redirect, flash
from flask_wtf import FlaskForm
from wtforms import StringField, PasswordField, SubmitField
from wtforms.validators import DataRequired, Length, Email, EqualTo
app = Flask(__name__)
app.config['SECRET_KEY'] = 'your_secret_key' # 必须设置,否则 CSRF 保护无法使用
(2) 定义表单
使用 FlaskForm
继承 WTForms
,定义表单字段和验证规则:
class LoginForm(FlaskForm):
email = StringField('邮箱', validators=[DataRequired(), Email()])
password = PasswordField('密码', validators=[DataRequired(), Length(min=6, max=12)])
submit = SubmitField('登录')
✅ DataRequired()
不能为空
✅ Email()
必须是合法邮箱格式
✅ Length(min=6, max=12)
密码长度 6-12 位
(3) 创建视图
表单处理逻辑
@app.route('/login', methods=['GET', 'POST'])
def login():
form = LoginForm()
if form.validate_on_submit(): # 检查表单是否有效
email = form.email.data
password = form.password.data
flash(f'用户 {email} 登录成功', 'success')
return redirect('/success') # 登录成功跳转
return render_template('login.html', form=form)
✅ form.validate_on_submit()
自动检查 POST 数据是否符合验证规则
✅ flash()
用于在前端显示错误或成功信息
✅ form.email.data
获取表单数据
(4) 编写 HTML 表单
templates/login.html
:
<!DOCTYPE html>
<html lang="zh">
<head>
<meta charset="UTF-8">
<title>登录</title>
</head>
<body>
<h1>登录</h1>
{% with messages = get_flashed_messages(with_categories=true) %}
{% if messages %}
{% for category, message in messages %}
<p style="color: {{ 'green' if category == 'success' else 'red' }}">{{ message }}</p>
{% endfor %}
{% endif %}
{% endwith %}
<form method="POST">
{{ form.hidden_tag() }} {# CSRF 保护 #}
<p>
{{ form.email.label }} <br>
{{ form.email(size=30) }} <br>
{% for error in form.email.errors %}
<span style="color:red;">{{ error }}</span>
{% endfor %}
</p>
<p>
{{ form.password.label }} <br>
{{ form.password(size=30) }} <br>
{% for error in form.password.errors %}
<span style="color:red;">{{ error }}</span>
{% endfor %}
</p>
<p>{{ form.submit() }}</p>
</form>
</body>
</html>
✅ {{ form.hidden_tag() }}
用于 CSRF 保护
✅ form.email(size=30)
渲染表单输入框
✅ for error in form.email.errors
显示验证错误
3. 复杂表单示例(注册表单)
支持 两次密码一致性验证:
class RegisterForm(FlaskForm):
username = StringField('用户名', validators=[DataRequired(), Length(min=3, max=20)])
email = StringField('邮箱', validators=[DataRequired(), Email()])
password = PasswordField('密码', validators=[DataRequired(), Length(min=6, max=12)])
confirm_password = PasswordField('确认密码', validators=[DataRequired(), EqualTo('password', message="两次密码不一致")])
submit = SubmitField('注册')
✅ EqualTo('password')
验证两次密码一致
✅ message="两次密码不一致"
自定义错误提示
注册视图:
@app.route('/register', methods=['GET', 'POST'])
def register():
form = RegisterForm()
if form.validate_on_submit():
flash(f'用户 {form.username.data} 注册成功', 'success')
return redirect('/login')
return render_template('register.html', form=form)
4. 自定义验证器
可以自定义表单验证逻辑。例如:检查用户名是否已存在。
from wtforms.validators import ValidationError
class UniqueUsername:
"""自定义验证器,检查用户名是否已被使用"""
def __init__(self, message=None):
if not message:
message = "该用户名已被占用"
self.message = message
def __call__(self, form, field):
existing_users = ["admin", "test"] # 假设数据库已有的用户名
if field.data in existing_users:
raise ValidationError(self.message)
class RegisterForm(FlaskForm):
username = StringField('用户名', validators=[DataRequired(), Length(min=3, max=20), UniqueUsername()])
email = StringField('邮箱', validators=[DataRequired(), Email()])
password = PasswordField('密码', validators=[DataRequired(), Length(min=6, max=12)])
confirm_password = PasswordField('确认密码', validators=[DataRequired(), EqualTo('password')])
submit = SubmitField('注册')
✅ UniqueUsername()
检查用户名是否已注册
✅ raise ValidationError(self.message)
触发错误
5. 结论
Flask-WTF
是WTForms
的 Flask 扩展,提供 表单验证、CSRF 保护。FlaskForm
定义表单字段 & 验证规则,如DataRequired()
、Email()
。form.validate_on_submit()
自动检查表单数据。- HTML 使用
form.hidden_tag()
保护 CSRF,用form.errors
显示错误。 - 支持自定义验证器,如检查用户名是否唯一。
Flask + WTForms 让表单验证更安全、更易用!🚀