python第一百一十七天-----ModelForm組件
阿新 • • 發佈:2017-09-01
csrf clu 信息 執行過程 time_zone lean char 用戶名 caption
Model + Form => 驗證 + 數據庫操作
- class LoginModelForm(xxxxx):
利用model.A中的字段
1. 生成HTML標簽:class Meta: ...
2. mf = xxxModelForm(instance=ModelObj)
3. 額外的標簽, is_rmb = Ffields.CharField(widget=Fwidgets.CheckboxInput())
4. 各種驗證 is_valid() -> 各種鉤子...
5. mf.save()
# 或
instance = mf.save(False)
instance.save()
mf.save_m2m()
a. class Meta:
1 model, # 對應Model的 2 fields=None, # 字段 3 exclude=None, # 排除字段 4 labels=None, # 提示信息 5 help_texts=None, # 幫助提示信息 6 widgets=None, #View Code自定義插件 7 error_messages=None, # 自定義錯誤信息(整體錯誤信息from django.core.exceptions import NON_FIELD_ERRORS) 8 field_classes=None # 自定義字段類 (也可以自定義字段) 9 localized_fields=(‘birth_date‘,) # 本地化,如:根據不同時區顯示數據 10 如: 11 數據庫中12 2016-12-27 04:10:57 13 setting中的配置 14 TIME_ZONE = ‘Asia/Shanghai‘ 15 USE_TZ = True 16 則顯示: 17 2016-12-27 12:10:57
b. 驗證執行過程
is_valid -> full_clean -> 鉤子 -> 整體錯誤
c. 字典字段驗證
def clean_字段名(self):
# 可以拋出異常
# from django.core.exceptions import ValidationError
return "新值"
d. 用於驗證
model_form_obj = XXOOModelForm()
model_form_obj.is_valid()
model_form_obj.errors.as_json()
model_form_obj.clean()
model_form_obj.cleaned_data
e. 用於創建
model_form_obj = XXOOModelForm(request.POST)
#### 頁面顯示,並提交 #####
# 默認保存多對多
obj = form.save(commit=True)
# 不做任何操作,內部定義 save_m2m(用於保存多對多)
obj = form.save(commit=False)
obj.save() # 保存單表信息
obj.save_m2m() # 保存關聯多對多信息
f. 用於更新和初始化
obj = model.tb.objects.get(id=1)
model_form_obj = XXOOModelForm(request.POST,instance=obj)
...
PS: 單純初始化
model_form_obj = XXOOModelForm(initial={...})
示例:
index.html
1 <!DOCTYPE html> 2 <html lang="en"> 3 <head> 4 <meta charset="UTF-8"> 5 <title></title> 6 </head> 7 <body> 8 <form action="/index/" method="POST"> 9 {% csrf_token %} 10 {{ obj.as_p }} 11 <input type="submit" value="提交" /> 12 </form> 13 </body> 14 </html>
models.py
1 from django.db import models 2 3 # Create your models here. 4 5 6 class UserType(models.Model): 7 caption = models.CharField(max_length=32) 8 9 10 class UserGroup(models.Model): 11 name = models.CharField(max_length=32) 12 13 14 class UserInfo(models.Model): 15 username = models.CharField(max_length=32) 16 email = models.EmailField() 17 user_type = models.ForeignKey(to=‘UserType‘,to_field=‘id‘) 18 u2g = models.ManyToManyField(UserGroup)
views.py
1 from django.shortcuts import render,HttpResponse 2 from app01 import models 3 4 from django import forms 5 from django.forms import fields as Ffields 6 from django.forms import widgets as Fwidgets#插件 as 設置別名 7 8 class UserInfoModelForm(forms.ModelForm): 9 #自定義字段可以在前端展示 ,不與數據庫關聯 10 is_rmb = Ffields.CharField(widget=Fwidgets.CheckboxInput()) 11 class Meta: 12 model = models.UserInfo#指定到一個類(表)中的字段 13 fields = ‘__all__‘#所有字段 (列) 14 # fields = [‘username‘,‘email‘]#可以指定的列 15 # exclude = [‘username‘]#排除指定項 16 #定義標簽 17 labels = { 18 ‘username‘: ‘用戶名‘, 19 ‘email‘: ‘郵箱‘, 20 } 21 help_texts = {#幫助提示信息 22 ‘username‘: ‘...‘ 23 } 24 widgets = {#自定義插件 使用 form的插件 25 ‘username‘: Fwidgets.Textarea(attrs={‘class‘: ‘c1‘}) 26 } 27 error_messages = { 28 ‘__all__‘:{ 29 #整體的錯誤信息 30 }, 31 ‘email‘: {#指定的錯誤信息 32 ‘required‘: ‘郵箱不能為空‘, 33 ‘invalid‘: ‘郵箱格式錯誤..‘, 34 } 35 } 36 field_classes = {#字段的類 37 # ‘email‘: Ffields.URLField 38 } 39 40 # localized_fields=(‘ctime‘,) 41 42 def clean_username(self): 43 old = self.cleaned_data[‘username‘] 44 return old 45 46 class UserInfoForm(forms.Form): 47 username = Ffields.CharField(max_length=32) 48 email = Ffields.EmailField() 49 user_type = Ffields.ChoiceField( 50 #從數據庫取值 51 choices=models.UserType.objects.values_list(‘id‘,‘caption‘)#取選 項列表 52 ) 53 #重寫父類 54 def __init__(self, *args, **kwargs): 55 super(UserInfoForm,self).__init__(*args, **kwargs) 56 self.fields[‘user_type‘].choices = models.UserType.objects.values_list(‘id‘,‘caption‘)#更新數據 57 58 59 def index(request): 60 if request.method == "GET": 61 obj = UserInfoModelForm() 62 return render(request,‘index.html‘,{‘obj‘: obj}) 63 elif request.method == "POST": 64 obj = UserInfoModelForm(request.POST) 65 if obj.is_valid(): 66 # obj.save()#完成所有對應關系的保存 67 instance = obj.save(False)#手動對應關系進行保存 68 instance.save()#只保存表的數據 69 obj.save_m2m()#保存對應表的關系的表 70 71 72 # print(obj.is_valid()) 73 # print(obj.cleaned_data) 74 # print(obj.errors.as_json()) 75 return render(request,‘index.html‘,{‘obj‘: obj}) 76 77 #用戶列表 78 def user_list(request):# 所有 跨表條件 79 li = models.UserInfo.objects.all().select_related(‘user_type‘) 80 return render(request,‘user_list.html‘,{‘li‘: li}) 81 #用戶信息編輯 82 def user_edit(request, nid): 83 # 獲取當前id對象的用戶信息 84 # 顯示用戶已經存在數據 85 if request.method == "GET": 86 user_obj = models.UserInfo.objects.filter(id=nid).first() 87 #調用ModelForm 默認值 88 mf = UserInfoModelForm(instance=user_obj) 89 return render(request,‘user_edit.html‘,{‘mf‘: mf, ‘nid‘: nid}) 90 elif request.method == ‘POST‘: 91 user_obj = models.UserInfo.objects.filter(id=nid).first() 92 mf = UserInfoModelForm(request.POST,instance=user_obj) 93 if mf.is_valid(): 94 95 mf.save() 96 else: 97 print(mf.errors.as_json()) 98 return render(request,‘user_edit.html‘,{‘mf‘: mf, ‘nid‘: nid})View Code
user_list.html
1 <!DOCTYPE html> 2 <html lang="en"> 3 <head> 4 <meta charset="UTF-8"> 5 <title></title> 6 </head> 7 <body> 8 <ul> 9 {% for row in li %} 10 <li>{{ row.username }} - {{ row.user_type.caption }} - <a href="/edit-{{ row.id }}/">編輯</a></li> 11 {% endfor %} 12 </ul> 13 </body> 14 </html>
user_edit.html
1 <!DOCTYPE html> 2 <html lang="en"> 3 <head> 4 <meta charset="UTF-8"> 5 <title></title> 6 </head> 7 <body> 8 <form method="POST" action="/edit-{{ nid }}/"> 9 {% csrf_token %} 10 {{ mf.as_p }} 11 <!--顯示當前對象的所有信息--> 12 <input type="submit" value="提交" /> 13 </form> 14 15 </body> 16 </html>
python第一百一十七天-----ModelForm組件