formOoject.is_valid()调用如下方法:
return self.is_bound and not self.error
其中is_bound可以认为是否是有传入(绑定)
重点是self.error
进入这个方法‘
1 @property 2 def errors(self): 3 "Returns an ErrorDict for the data provided for the form" 4 if self._errors is None: 5 self.full_clean() 6 return self._errors
从第5行得知,这个方法的核心是full_clean(),查看他的方法:
1 def full_clean(self): 2 """ 3 Cleans all of self.data and populates self._errors and 4 self.cleaned_data. 5 """ 6 self._errors = ErrorDict() 7 if not self.is_bound: # Stop further processing. 8 return 9 self.cleaned_data = {} 10 # If the form is permitted to be empty, and none of the form data has 11 # changed from the initial data, short circuit any validation. 12 if self.empty_permitted and not self.has_changed(): 13 return 14 15 self._clean_fields() 16 self._clean_form() 17 self._post_clean()
重点在于15,16,17行
首先查看15行的实现:
1 def _clean_fields(self): 2 for name, field in self.fields.items(): 3 # value_from_datadict() gets the data from the data dictionaries. 4 # Each widget type knows how to retrieve its own data, because some 5 # widgets split data over several HTML fields. 6 if field.disabled: 7 value = self.get_initial_for_field(field, name) 8 else: 9 value = field.widget.value_from_datadict(self.data, self.files, self.add_prefix(name)) 10 try: 11 if isinstance(field, FileField): 12 initial = self.get_initial_for_field(field, name) 13 value = field.clean(value, initial) 14 else: 15 value = field.clean(value) 16 self.cleaned_data[name] = value 17 if hasattr(self, ‘clean_%s‘ % name): 18 value = getattr(self, ‘clean_%s‘ % name)() 19 self.cleaned_data[name] = value 20 except ValidationError as e: 21 self.add_error(name, e)
注意17,18行;这里提供了一个钩子.既 clean_字段 ,这里通过反射的形式进行调用
接下来是16行:
1 def _clean_form(self): 2 try: 3 cleaned_data = self.clean() 4 except ValidationError as e: 5 self.add_error(None, e) 6 else: 7 if cleaned_data is not None: 8 self.cleaned_data = cleaned_data
这里,第3行调用了钩子,我们可以覆写这个方法
最后是17行:
1 def _post_clean(self): 2 """ 3 An internal hook for performing additional cleaning after form cleaning 4 is complete. Used for model validation in model forms. 5 """ 6 pass
钩子