flask wtforms 在同一 html 页面和同一 route/view 页面上显示 2 个表单的验证错误
flask wtforms showing validation error on 2 forms on the same html page and same route/view
所以我在 home.html 上有 2 个表单,登录表单和注册表,它们显示为模态单击登录按钮时,如下所示:
home.html
<button type="button" class="btn btn-outline-danger" data-bs-toggle="modal" data-bs-target="#loginModal">
Login
</button>
<div class="modal fade" id="loginModal" tabindex="-1" aria-labelledby="exampleModalLabel" aria-hidden="true">
<div class="modal-dialog">
<div class="modal-content">
<div class="modal-header">
<h5 class="modal-title" id="exampleModalLabel">Sign In</h5>
<button type="button" class="btn-close" data-bs-dismiss="modal" aria-label="Close"></button>
</div>
<div class="modal-body">
<button id="login" class="btn btn-login btn-md">Log In</button>
<button id="regis" class="btn btn-login btn-md">Register</button><hr style="margin-top: 0px;">
<div class="" id="login">
<form method="POST" action="">
{{ login_form.hidden_tag() }}
<fieldset class="form-group">
<div class="form-group">
{% if login_form.email_login.errors %}
{{ login_form.email_login(class="form-control form-control-md is-invalid") }}
<div class="invalid-feedback">
{% for error in login_form.email_login.errors %}
<span>{{ error }}</span>
{% endfor %}
</div>
{% else %}
{{ login_form.email_login(class="form-control form-control-md mb-2", placeholder="Email") }}
{% endif %}
</div>
<div class="form-group">
{% if login_form.password_login.errors %}
{{ login_form.password_login(class="form-control form-control-md is-invalid") }}
<div class="invalid-feedback">
{% for error in login_form.password_login.errors %}
<span>{{ error }}</span>
{% endfor %}
</div>
{% else %}
{{ login_form.password_login(class="form-control form-control-md mb-2", placeholder="Password") }}
{% endif %}
</div>
<div class="form-check">
{{ login_form.remember(class="form-check-input") }}
{{ login_form.remember.label(class="form-check-label") }}
</div>
</fieldset>
<div class="form-group">
{{ login_form.submit_login(class="btn btn-danger") }}
<small class="text-muted ml-2">
<a href="">Forgot Password?</a>
</small>
</div>
</form>
</div>
<div class="" id="regis">
<form method="POST" action="">
{{ regis_form.hidden_tag() }}
<fieldset class="form-group">
<div class="form-group">
{% if regis_form.username_regis.errors %}
{{ regis_form.username_regis(class="form-control form-control-md is-invalid") }}
<div class="invalid-feedback">
{% for error in regis_form.username_regis.errors %}
<span>{{ error }}</span>
{% endfor %}
</div>
{% else %}
{{ regis_form.username_regis(class="form-control form-control-md mb-2", placeholder="Username") }}
{% endif %}
</div>
<div class="form-group">
{% if regis_form.email_regis.errors %}
{{ regis_form.email_regis(class="form-control form-control-md is-invalid") }}
<div class="invalid-feedback">
{% for error in regis_form.email_regis.errors %}
<span>{{ error }}</span>
{% endfor %}
</div>
{% else %}
{{ regis_form.email_regis(class="form-control form-control-md mb-2", placeholder="Email") }}
{% endif %}
</div>
<div class="form-group">
{% if regis_form.password_regis.errors %}
{{ regis_form.password_regis(class="form-control form-control-md is-invalid") }}
<div class="invalid-feedback">
{% for error in regis_form.password_regis.errors %}
<span>{{ error }}</span>
{% endfor %}
</div>
{% else %}
{{ regis_form.password_regis(class="form-control form-control-md mb-2", placeholder="Password") }}
{% endif %}
</div>
</fieldset>
<div class="form-group">
{{ regis_form.submit_regis(class="btn btn-danger") }}
</div>
</form>
</div>
</div>
</div>
</div>
</div>
“登录”和“注册”这两个按钮是选项卡,即通过单击“注册”按钮,您将看到由 JavaScript 控制的注册表单,反之亦然。
我的 forms.py 文件如下所示:
forms.py
class RegistrationForm(FlaskForm):
username_regis = StringField('Username',
validators=[DataRequired(), Length(min=2, max=20)])
email_regis = StringField('Email',
validators=[DataRequired(), Email()])
password_regis = PasswordField('Password', validators=[DataRequired()])
submit_regis = SubmitField('Sign Up')
class LoginForm(FlaskForm):
email_login = StringField('Email',
validators=[DataRequired(), Email()])
password_login = PasswordField('Password', validators=[DataRequired()])
remember = BooleanField('Remember Me')
submit_login = SubmitField('Login')
下面是routes.py函数:
routes.py
@app.route("/", methods=['GET', 'POST'])
def home():
login_form = LoginForm()
regis_form = RegistrationForm()
if request.method == 'POST':
if login_form.validate_on_submit() and login_form.submit_login.data:
user = User.query.filter_by(email=login_form.email_login.data).first()
if user and bcrypt.check_password_hash(user.password, login_form.password_login.data):
login_user(user, remember=login_form.remember.data)
next_page = request.args.get('next')
return redirect(next_page) if next_page else redirect(url_for('home'))
else:
flash('Login Unsuccessful. Please check email and password', 'danger')
if regis_form.validate_on_submit() and regis_form.submit_regis.data:
hashed_password = bcrypt.generate_password_hash(regis_form.password_regis.data).decode('utf-8')
user = User(username=regis_form.username_regis.data, email=regis_form.email_regis.data, password=hashed_password)
db.session.add(user)
db.session.commit()
flash('Your account has been created! You are now able to log in', 'success')
return redirect(url_for('home'))
return render_template('home.html', login_form=login_form, regis_form=regis_form)
现在,问题是当我尝试使用未注册的电子邮件登录时,它会闪烁
'Login Unsuccessful. Please check email and password'
没关系,因为它应该这样做。但是当我再次打开登录模式并打开注册选项卡时,* username_regis password_regis 和 email_regis* 字段显示 'The field is required' 错误。
注册表单上不应显示此错误,因为我从未提交过此表单。
我想摆脱这些错误信息。我将非常感谢任何帮助。
你写的代码如下:
if request.method == 'POST':
if login_form.validate_on_submit() and login_form.submit_login.data:
<SNIP>
if regis_form.validate_on_submit() and regis_form.submit_regis.data:
<SNIP>
这意味着无论您提交什么表格,两个 表格都经过验证。因此,当您提交一个表单时,另一个表单将始终显示错误。 首选解决方案是post到不同的路线。在您的表单上,需要填写 action
参数,并且您需要两个函数,每个函数对应一个路径。您也将摆脱询问表单数据是否可用的问题。一定是,因为你在那条路上。
所以我在 home.html 上有 2 个表单,登录表单和注册表,它们显示为模态单击登录按钮时,如下所示:
home.html
<button type="button" class="btn btn-outline-danger" data-bs-toggle="modal" data-bs-target="#loginModal">
Login
</button>
<div class="modal fade" id="loginModal" tabindex="-1" aria-labelledby="exampleModalLabel" aria-hidden="true">
<div class="modal-dialog">
<div class="modal-content">
<div class="modal-header">
<h5 class="modal-title" id="exampleModalLabel">Sign In</h5>
<button type="button" class="btn-close" data-bs-dismiss="modal" aria-label="Close"></button>
</div>
<div class="modal-body">
<button id="login" class="btn btn-login btn-md">Log In</button>
<button id="regis" class="btn btn-login btn-md">Register</button><hr style="margin-top: 0px;">
<div class="" id="login">
<form method="POST" action="">
{{ login_form.hidden_tag() }}
<fieldset class="form-group">
<div class="form-group">
{% if login_form.email_login.errors %}
{{ login_form.email_login(class="form-control form-control-md is-invalid") }}
<div class="invalid-feedback">
{% for error in login_form.email_login.errors %}
<span>{{ error }}</span>
{% endfor %}
</div>
{% else %}
{{ login_form.email_login(class="form-control form-control-md mb-2", placeholder="Email") }}
{% endif %}
</div>
<div class="form-group">
{% if login_form.password_login.errors %}
{{ login_form.password_login(class="form-control form-control-md is-invalid") }}
<div class="invalid-feedback">
{% for error in login_form.password_login.errors %}
<span>{{ error }}</span>
{% endfor %}
</div>
{% else %}
{{ login_form.password_login(class="form-control form-control-md mb-2", placeholder="Password") }}
{% endif %}
</div>
<div class="form-check">
{{ login_form.remember(class="form-check-input") }}
{{ login_form.remember.label(class="form-check-label") }}
</div>
</fieldset>
<div class="form-group">
{{ login_form.submit_login(class="btn btn-danger") }}
<small class="text-muted ml-2">
<a href="">Forgot Password?</a>
</small>
</div>
</form>
</div>
<div class="" id="regis">
<form method="POST" action="">
{{ regis_form.hidden_tag() }}
<fieldset class="form-group">
<div class="form-group">
{% if regis_form.username_regis.errors %}
{{ regis_form.username_regis(class="form-control form-control-md is-invalid") }}
<div class="invalid-feedback">
{% for error in regis_form.username_regis.errors %}
<span>{{ error }}</span>
{% endfor %}
</div>
{% else %}
{{ regis_form.username_regis(class="form-control form-control-md mb-2", placeholder="Username") }}
{% endif %}
</div>
<div class="form-group">
{% if regis_form.email_regis.errors %}
{{ regis_form.email_regis(class="form-control form-control-md is-invalid") }}
<div class="invalid-feedback">
{% for error in regis_form.email_regis.errors %}
<span>{{ error }}</span>
{% endfor %}
</div>
{% else %}
{{ regis_form.email_regis(class="form-control form-control-md mb-2", placeholder="Email") }}
{% endif %}
</div>
<div class="form-group">
{% if regis_form.password_regis.errors %}
{{ regis_form.password_regis(class="form-control form-control-md is-invalid") }}
<div class="invalid-feedback">
{% for error in regis_form.password_regis.errors %}
<span>{{ error }}</span>
{% endfor %}
</div>
{% else %}
{{ regis_form.password_regis(class="form-control form-control-md mb-2", placeholder="Password") }}
{% endif %}
</div>
</fieldset>
<div class="form-group">
{{ regis_form.submit_regis(class="btn btn-danger") }}
</div>
</form>
</div>
</div>
</div>
</div>
</div>
“登录”和“注册”这两个按钮是选项卡,即通过单击“注册”按钮,您将看到由 JavaScript 控制的注册表单,反之亦然。
我的 forms.py 文件如下所示:
forms.py
class RegistrationForm(FlaskForm):
username_regis = StringField('Username',
validators=[DataRequired(), Length(min=2, max=20)])
email_regis = StringField('Email',
validators=[DataRequired(), Email()])
password_regis = PasswordField('Password', validators=[DataRequired()])
submit_regis = SubmitField('Sign Up')
class LoginForm(FlaskForm):
email_login = StringField('Email',
validators=[DataRequired(), Email()])
password_login = PasswordField('Password', validators=[DataRequired()])
remember = BooleanField('Remember Me')
submit_login = SubmitField('Login')
下面是routes.py函数:
routes.py
@app.route("/", methods=['GET', 'POST'])
def home():
login_form = LoginForm()
regis_form = RegistrationForm()
if request.method == 'POST':
if login_form.validate_on_submit() and login_form.submit_login.data:
user = User.query.filter_by(email=login_form.email_login.data).first()
if user and bcrypt.check_password_hash(user.password, login_form.password_login.data):
login_user(user, remember=login_form.remember.data)
next_page = request.args.get('next')
return redirect(next_page) if next_page else redirect(url_for('home'))
else:
flash('Login Unsuccessful. Please check email and password', 'danger')
if regis_form.validate_on_submit() and regis_form.submit_regis.data:
hashed_password = bcrypt.generate_password_hash(regis_form.password_regis.data).decode('utf-8')
user = User(username=regis_form.username_regis.data, email=regis_form.email_regis.data, password=hashed_password)
db.session.add(user)
db.session.commit()
flash('Your account has been created! You are now able to log in', 'success')
return redirect(url_for('home'))
return render_template('home.html', login_form=login_form, regis_form=regis_form)
现在,问题是当我尝试使用未注册的电子邮件登录时,它会闪烁 'Login Unsuccessful. Please check email and password' 没关系,因为它应该这样做。但是当我再次打开登录模式并打开注册选项卡时,* username_regis password_regis 和 email_regis* 字段显示 'The field is required' 错误。
注册表单上不应显示此错误,因为我从未提交过此表单。
我想摆脱这些错误信息。我将非常感谢任何帮助。
你写的代码如下:
if request.method == 'POST':
if login_form.validate_on_submit() and login_form.submit_login.data:
<SNIP>
if regis_form.validate_on_submit() and regis_form.submit_regis.data:
<SNIP>
这意味着无论您提交什么表格,两个 表格都经过验证。因此,当您提交一个表单时,另一个表单将始终显示错误。 首选解决方案是post到不同的路线。在您的表单上,需要填写 action
参数,并且您需要两个函数,每个函数对应一个路径。您也将摆脱询问表单数据是否可用的问题。一定是,因为你在那条路上。