检查两个字段
本课属于 Coddy Django 学习旅程的“表单”单元。第 11 课,共 20 课。
冬季书展持续 3 天,结束日期不能早于开始日期。clean_<field> 方法只检查一个字段,因此跨字段的规则要写在 clean() 中,它会在每个字段完成自己的检查后运行。以下是一个预订表单示例,团体人数超过 6 人时必须填写电话号码:
def clean(self):
cleaned_data = super().clean()
guests = cleaned_data.get("guests")
phone = cleaned_data.get("phone")
if guests and guests > 6 and not phone:
raise forms.ValidationError("Groups over 6 need a phone number.")
return cleaned_data检查失败的字段不会出现在 cleaned_data 中,可选日期为空时值为 None,因此要用 .get() 读取,并且只在两个值都存在时进行比较。
在 clean() 中引发的错误属于整个表单,因此字段循环不会显示它。{{ form.non_field_errors }} 会显示它。
挑战
中等为活动添加结束日期。
- 在
events/forms.py中,向EventForm添加一个可选的end_date日期字段。编写clean():当两个日期都存在且结束日期早于开始日期时,抛出The event cannot end before it starts.。使用.get()读取日期。 - 在
new_event中,也保存end_date。 - 在
new_event.html中,在循环上方显示form.non_field_errors。
把结束日期设为早于开始日期,你就会看到这条消息。
亲手试试
import datetime
from django import forms
class EventForm(forms.Form):
title = forms.CharField(max_length=100)
date = forms.DateField()
place = forms.CharField(max_length=100)
description = forms.CharField(widget=forms.Textarea, required=False)
capacity = forms.IntegerField(min_value=1)
def clean_date(self):
date = self.cleaned_data["date"]
if date < datetime.date.today():
raise forms.ValidationError("The date cannot be in the past.")
return date
这节课包含一个小测验。开始学习即可作答,并记录你的进度。
表单中的所有课
自己练习: Django 在线编辑器