from django import forms class TitleSearch(forms.Form): title=forms.CharField(label='书名',label_suffix='',error_messages={'required':'请输入正确的title'})如上代码所示,Django 规定,所有的 Form 对象都必须继续自 django.forms.Form;我们定义了一个 title 属性,它是 forms.CharField 类型的,而该字段类型继承于基类 Field,每个 Field 字段类型都有个默认的属性 required=True 代表该字段是必填选项。那么 Form 对象有哪些特性呢?我们依次进行回顾。
class TestForm(forms.Form): a = forms.CharField(required=False)#a不是必填字段,可以不提供 b=forms.CharField(max_length=20)#最大长度为20 c=forms.IntegerField(max_value=10,min_value=1)#最大值为10最小值1实例测试过程如下所示:
In [1]: from index.forms import TestForm In [1]: from index.forms import TestForm In [2]: pl=TestForm({"b":"django","c":4}) In [3]: pl.is_valid() Out[3]: True In [4]: pl=TestForm({"b":"django","c":11}) In [5]: pl.is_valid() Out[5]: False In [6]: pl=TestForm({"a":"python","c":11}) In [7]: pl.is_valid() Out[7]: False综上所述,可以看出 is_valid() 方法的验证作用,验证返回 True 的表单,证明数据验证结果为真,该表单可以使用。验证生效后的表单会有一个 cleaned_data 属性,表单对象就是通过这个属性对传递进来的数据做清理的,把值转换成合适的 Python 类型。对于返回 False 的实例,我们可以使用 errors 属性查看其错误信息。如下所示:
In [2]: pl=ExampleForm({"a":"python","c":11}) In [3]: pl.is_valid() Out[3]: False In [4]: pl.errors Out[4]: {'b': ['这个字段是必填项。'], 'c': ['确保该值小于或等于10。']}errors 是 django.forms.utils.ErrorDict 类型的实例,它是 Python 字典的类型的子类,所以我们可以使用如下方式查看错误信息:
In [1]: pl["c"].errors Out[1]: ['确保该值小于或等于10。']简单总结一下,通常在使用表单对象时,会传递参数初始化表单实例,调用其 is_valid 方法,如果为 True,则从 cleaned_data 属性中获取清理之后的字段值,否则,返回错误的信息提示,另外主要注意 cleaned_data 和 is_valid 的执行顺序,即验证不成功的话,就不会存在 cleaned_data 属性。
In [12]: pl=ExampleForm({"b":"django","c":10}) In [13]: print(pl["b"]) <input type="text" name="b" value="django" maxlength="20" required id="id_b">由于表单实例可以直接返回 HTML表单元素,所以,可以用它来替换模板文件中的字段定义,而且在没有正确填充表单时,它还可以返回错误信息的提示。
#index\views.py from index.forms import TitleSearch #引入forms.py中定义的TitleSearch类 def search_ttile_form(request): return render(request,'index/search_title.html',context={'form':TitleSearch()})#实例化表单对象 def search_title(request): form=TitleSearch(request.GET) if form.is_valid():#第一步验证成功 books=Book.objects.filter(title__icontains=form.cleaned_data["title"])#调用cleaned_data属性获取清理后的数据 if not books: return HttpResponseRedirect("/index/book_not_list") return render(request,'index/book_list.html',locals()) 查看返回结果 else: # 将带有错误信息的表单实例作为上下文传递到需要渲染的模板中 return render(request,'index/search_title.html',{'form':form})修改 search_title.html 页面代码,如下所示:
<!--修改表单模板--> <!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <title>书籍搜索页面</title> </head> <body> <form action="/index/search_title/" method="get"> {{ form }} <input type="submit" value="查询一下"> </form> </body> </html>然后将 book_list.html 更改为如下代码:
<!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <title>搜索结果显示</title> </head> <body> <table border="1"> <tr> <th>id</th> <th>title</th> <th>price</th> <th> retail_price</th> <th>public</th> </tr> {% for book in books %} <tr> <td>{{ book.id }}</td> <td>{{ book.title }}</td> <td>{{ book.price }}</td> <td>{{ book.retail_price }}</td> <!--外键关联字段取值--> <td>{{ book.pub.pubname}}</td> </tr> {% endfor %} </table> </body> </html>最后新建 book_not_list.html 页面编写如下代码:
<!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <title>书籍搜索页面</title> </head> <body> <h2>对不起,没找到您需要的书籍</h2> </body> </html>并简单编写 book_not_list 视图函数,最后配置相应的路由映射关系,如下所示:
#index\views.py def book_not_list(request): return render(request,"index/book_not_list.html") #index\urls.py urlpatterns=[path('book_not_list/',views.book_not_list)]至于其他路由映射关系无需改变,然后访问 127.0.0.1/index/search_title/,进行书籍 title 的搜索即可,可得如下页面:
Copyright © 广州京杭网络科技有限公司 2005-2025 版权所有 粤ICP备16019765号
广州京杭网络科技有限公司 版权所有