我的表单验证几乎完成了,我只知道两个我不知道如何解决的情况:1)当然需要密码字段,但我也提供了通过OAuth登录google或facebook帐户的可能性,然后name被预先填充,但如果有用户,我会从表单中完全删除密码字段(google)或facebook用户对象:
<tr><td>
<br /> {% if user or current_user %} {% else %}
<div class="labelform">
{% filter capitalize %}{% trans %}password{% endtrans %}{% endfilter %}:
</div>
</td><td> <div class="adinput">{{ form.password|safe }}{% trans %}Choose a password{% endtrans %}</div>{% endif %}
</td></tr>
所以对于那些已经登录并且密码字段没有意义的用户,我需要一些逻辑使该字段有条件地成为可选字段。我想我可以在我的表单类中有一个用于登录的变量+一个方法,例如:
class AdForm(Form):
logged_in = False
my_choices = [('1', _('VEHICLES')), ('2', _('Cars')), ('3', _('Bicycles'))]
name = TextField(_('Name'), [validators.Required(message=_('Name is required'))], widget=MyTextInput())
title = TextField(_('title'), [validators.Required(message=_('Subject is required'))], widget=MyTextInput())
text = TextAreaField(_('Text'),[validators.Required(message=_('Text is required'))], widget=MyTextArea())
phonenumber = TextField(_('Phone number'))
phoneview = BooleanField(_('Display phone number on site'))
price = TextField(_('Price'),[validators.Regexp('\d', message=_('This is not an integer number, please see the example and try again')),validators.Optional()] )
password = PasswordField(_('Password'),[validators.Optional()], widget=PasswordInput())
email = TextField(_('Email'), [validators.Required(message=_('Email is required')), validators.Email(message=_('Your email is invalid'))], widget=MyTextInput())
category = SelectField(choices = my_choices, default = '1')
def validate_name(form, field):
if len(field.data) > 50:
raise ValidationError(_('Name must be less than 50 characters'))
def validate_email(form, field):
if len(field.data) > 60:
raise ValidationError(_('Email must be less than 60 characters'))
def validate_price(form, field):
if len(field.data) > 8:
raise ValidationError(_('Price must be less than 9 integers'))
def validate_password(form, field):
if not logged_in and not field:
raise ValidationError(_('Password is required'))
上述验证密码是否能达到预期效果?还有更好的办法吗?我可以想到的另一种方法是有两个不同的表单类,在http post中,我实例化了表单类,它应该是:
def post(self):
if not current_user:
form = AdForm(self.request.params)
if current_user:
form = AdUserForm(self.request.params)
我还需要对category字段进行条件验证,选择某个类别后,会出现更多的选项,这些选项应仅对某个基本类别进行验证,例如,用户选择“汽车”,然后通过Ajax可以选择汽车的注册数据和里程数,如果选择了汽车类别,则这些字段是必需的。
所以这可能是两个问题,但这两个问题都与我如何使字段成为“有条件可选”或“有条件必需”有关。
我的表格是这样的
而对于一个登录的用户,我在名字和电子邮件地址前加上前缀,而pasword字段根本不使用,因此password字段既不适合“可选”也不适合“必需”,它需要类似“有条件可选”或“有条件必需”的内容
谢谢你的回答或评论
来自@dcrosta的答案很好,但是我认为自从这个答案之后,wtforms中的一些事情已经发生了变化。从
DataRequired
继承会将required
属性添加到表单字段,因此不会调用条件验证器。我对使用wtforms 2.1的@dcrosta类做了一个小更改。这只会超过field_flags
,因此浏览器验证不会完成。更理想的解决方案是在浏览器中进行验证,就像
DataRequired
的当前行为一样。我发现这个问题很有用,并且基于@dcrosta的答案,我创建了另一个可选的验证器。这样做的好处是,您可以将它与其他wtforms验证器结合起来。这是检查另一个字段的可选验证器。因为我需要根据某个值检查另一个字段的值,所以添加了一个自定义值检查:
我不确定这是否完全符合您的需要,但我以前在字段上使用过
RequiredIf
自定义验证器,这使得如果另一个字段具有表单中的值,则需要一个字段。。。例如,在datetime和timezone场景中,如果用户输入了datetime,我可以将timezone字段设置为具有值。构造器采用另一个字段的名称,该字段触发使该字段成为必需字段,例如:
这可能是实现所需逻辑的良好起点。
相关问题 更多 >
编程相关推荐