当日期字段的值小于当前日期(基于另一个SO答案(Django: How to set DateField to only accept Today & Future dates)时,尝试使用此(https://stackoverflow.com/a/22513989/8236733)SO帖子在模板中出现表单引发错误思想是通过表单字段验证器完成的(参见https://docs.djangoproject.com/en/2.0/ref/forms/validation/#cleaning-a-specific-field-attribute))。但是,在表单模板中输入所谓的无效值时,这似乎不起作用。
forms.py :
import datetime
from django import forms
from .models import Post
class MyForm(forms.Form):
title = forms.CharField(max_length=100, required=True, help_text='Give a title',
widget=forms.TextInput(attrs={'size': '50rem'}))
post = forms.CharField(max_length=280, required=True,
widget=forms.Textarea(attrs={'rows': 5}))
expire_date = forms.DateField(
widget=forms.TextInput(attrs=
{
'class':'datepicker', # to use jquery datepicker
}),
required=True
)
expire_time = forms.TimeField(
input_formats=['%H:%M %p'],
widget=forms.TextInput(attrs=
{
'class':'timepicker', # to use jquery timepicker
}),
required=True)
class Meta:
model = Post
fields = ('title', 'post', 'expire_date', 'expire_time',)
def clean_date(self): # see https://docs.djangoproject.com/en/dev/ref/forms/validation/#cleaning-a-specific-field-attribute
date = self.cleaned_data['expire_date']
print(date)
if date < datetime.date.today():
raise forms.ValidationError("The date cannot be in the past!")
return date
相关模板代码:
<form method="post">
{% csrf_token %}
{% for field in listing_form %}
<p>
{{ field.label_tag }}
<div class="ui input">{{ field }}</div>
{% if field.help_text %}
<small class="ui inverted">{{ field.help_text }}</small>
{% endif %}
{% for error in field.errors %}
<p style="color: red">{{ error }}</p>
{% endfor %}
</p>
{% endfor %}
<button class="ui inverted button" type="submit">submit</button>
<div class="ui divider"></div>
</small>
</form>
尝试提交带有过去日期的此表单不会在teplate中引发任何错误,并且表单的is_valid()方法在后端视图中不会引发任何错误。
django的新手,我在这里缺少什么?我是否需要以某种方式将验证方法附加到特定字段?
答案 0 :(得分:1)
显然,清除/验证特定表单字段的表单方法遵循特定的命名约定:clean_<field name>
非常重要。这在文档(https://docs.djangoproject.com/en/2.0/ref/forms/validation/#cleaning-a-specific-field-attribute)中隐式显示,但从未直接说明。更改原始帖子中表单类中的clean_...
方法以获得以下代码似乎解决了问题。
class MyForm(forms.Form):
....
expire_date = forms.DateField(
widget=forms.TextInput(attrs=
{
'class':'datepicker', # to use jquery datepicker
}),
required=True
)
....
class Meta:
model = Post
fields = ('title', 'post', 'expire_date', 'expire_time',)
def clean_expire_date(self):
date = self.cleaned_data['expire_date']
print(date)
if date < datetime.date.today():
raise forms.ValidationError("The date cannot be in the past!")
return date
如果有人知道文档中的哪个更明确地指定了这个命名约定,请告诉我。