form组件补充、modelform组件、django中间件

form组件补充、modelform组件、django中间件

form组件渲染标签

form组件的渲染标签比较强大,主要有三种方式:
# <p>forms组件渲染标签的方式1
(封装程度过高、扩展性差,主要用于本地测试):</p>
{{ form_obj.as_p }}
{{ form_obj.as_ul }}
{{ form_obj.as_table }}

# <p>forms组件渲染标签的方式2
(封装程度过低、扩展性高,编写麻烦)</p>
{{ form_obj.username.label }}
{{ form_obj.username }}
{{ form_obj.age.label }}
{{ form_obj.age }}
{{ form_obj.email.label }}
{{ form_obj.email }}

# <p>forms组件渲染标签的方式3
(封装程度较高、扩展性高,编写简单,推荐使用</p>
 {% for form in form_obj %}
 <p>
 {{ form.label }}
 {{ form }}
 </p>
 {% endfor %}
                       
'''
注意事项:
	forms组件只负责渲染获取用户数据的标签,也就意味着form标签与按钮都需要自己写
	前端的校验是弱不禁风的,最终都需要后端来校验。所以在使用forms组件的时候可以直接取消前端帮助校验
	<form action="" novalidate>  
	# 这个参数表示前端不要做任何校验直接交给后端来,完全靠后端来,不写的话前端会帮忙校验,如果不满足他的设定校验规则会有提示
'''

form组件展示信息

"""
后端不同请求返回的forms对象一定要是相同的变量名
"""
def ab_forms_func(request):
    # 1.产生一个空对象
    form_obj = MyForm()
    if request.method == 'POST':
        form_obj = MyForm(request.POST)  
        # request.POST可以看成一个字典直接传给forms类校验,字典内无论有多少键值对都没事,只需要关心类中编写多少
        if form_obj.is_valid():  # 校验数据是否合法
            print(form_obj.cleaned_data)  # 能够看到所有合法的数据
        else:
            print(form_obj.errors)  # 不合法的数据错误原因打印
    # 2.将该对象传递给html文件
    return render(request, 'formPage.html', locals())

    {% for form in form_obj %}
        <p>
            {{ form.label }}
            {{ form }}
            <span>{{ form.errors.0 }}</span>
        </p>
    {% endfor %}
'''
针对错误信息的提示可以修改成各国语言
'''

# 方式1:自定义内容
	给字段对象添加errors_messages参数
    username = forms.CharField(min_length=3, max_length=8, label='用户名', error_messages={
        'min_length': '用户名最少三个字符',
        'max_length': '用户名最多八个字符',
        'required': '用户名不能为空'
    })

# 方式2:修改系统语言环境
	from django.conf import global_settings  
    # django内部真正的配置文件
    汉字修改:
    # LANGUAGE_CODE = 'en-us'
    LANGUAGE_CODE = 'zh-hans'

form组件校验补充

forms组件针对字段数据的校验,提供了三种类型的校验方式(可以一起使用)
第一种类型:直接填写参数	max_length
第二种类型:使用正则表达式
validators=[
    RegexValidator(r'^[0-9]+$', '请输入数字'),
    RegexValidator(r'^159[0-9]+$', '数字必须以159开头'),
]
第三种类型:钩子函数,编写代码自定义校验规则
    
# 钩子函数>>>:校验最后一环 是在字段所有的校验参数之后触发
# 局部钩子:每次只校验一个字段数据,校验用户名是否存在
def clean_username(self):
    username = self.cleaned_data.get('username')
    if username == 'jason':
        self.add_error('username', '用户名jason已存在')
	return username  # 勾出来一个,返回一个

# 全局钩子:一次可以校验多个字段数据,校验两次密码是否一致
def clean(self):
    password = self.cleaned_data.get('password')
    confirm_pwd = self.cleaned_data.get('confirm_pwd')
    if not password == confirm_pwd:
        self.add_error('confirm_pwd', '两次密码不一致')
	return self.cleaned_data  # 勾出来全部,返回全部

form组件参数补充

min_length			最小字符
max_length			最大字符
min_value			最小值
max_value			最大值
label				字段注释
error_manages		错误提示
validators			正则校验器
initial				默认值
required			是否必填(false不填)
widget				控制标签的各项属性
widget=forms.widgets.PasswordInput(attrs={'class': 'form-control', 'username': 'jason'})
widget=forms.widgets.PasswordInput()  
# text=password
widget=forms.widgets.TextInput()  
# text=text

form组件源码剖析

切入口:
    form_obj.is_valid()
# 只有执行了is.valid方法后才能使用errors方法和cleaned_data查看数据的校验情况。

modelform组件

"""
我们学习校验性组件的目的 绝大部分是为了数据录入数据库之前的各项审核
forms组件使用的时候需要对照模型类编写代码 不够方便
"""
forms组件的强化版本 更好用更简单更方便!!!

# 常用参数介绍
model = models.Book  # 对应的Model中的类
fields = "__all__"  # 字段,如果是__all__,就是表示列出所有的字段
exclude = None  # 排除的字段
labels = None  # 提示信息
help_texts = None  # 帮助提示信息
widgets = None  # 自定义插件
error_messages = None  # 自定义错误信息

# modelform提供了一个save方法,可以帮我们保存数据。
(可以代替ORM的create和update操作
from django import forms
from app01 import models

class MyModelForm(forms.ModelForm):
    class Meta:
        model = models.UserInfo
        fields = '__all__'
        labels = {
            'username':'用户名'
        }

def ab_mf_func(request):
    modelform_obj = MyModelForm()
    if request.method == 'POST':
        modelform_obj = MyModelForm(request.POST,instance=User_obj)
        if modelform_obj.is_valid():
            modelform_obj.save()  # models.UserInfo.objects.create(...)/update(...)
        else:
            print(modelform_obj.errors)
    return render(request, 'modelFormPage.html', locals())

django中间件

django默认有七个中间件,并且还支持用户自定义中间件。
中间件主要可以用于:
    网站访问频率的校验,用户权限的校验等全局类型的功能需求。
  
MIDDLEWARE = [
    'django.middleware.security.SecurityMiddleware',
    'django.contrib.sessions.middleware.SessionMiddleware',
    'django.middleware.common.CommonMiddleware',
    # 'django.middleware.csrf.CsrfViewMiddleware',
    'django.contrib.auth.middleware.AuthenticationMiddleware',
    'django.contrib.messages.middleware.MessageMiddleware',
    'django.middleware.clickjacking.XFrameOptionsMiddleware',
]

如何自定义中间件:
    1.创建存储自定义中间件代码的py文件或者目录(如果中间件很多)
    2.参考自带中间件的代码编写类并继承
    3.在类中编写五个可以自定义的方法
    # (主要的是process_request和process_response)
    process_request(self,request)
    process_view(self, request, view_func, view_args, view_kwargs)
    process_template_response(self,request,response)
    process_exception(self, request, exception)
    process_response(self, request, response)

需要掌握:
# process_request
	1.请求来的时候会从上往下依次经过每一个注册了的中间件里面的该方法,如果没有则直接跳过
	2.如果该方法自己返回了HttpResponse对象那么不再往后执行而是直接原路返回(自定义的中间件返回HttpResponse)

# process_response
	1.响应走的时候会从下往上依次经过每一个注册了的中间件里面的该方法,如果没有则直接跳过
	2.该方法有两个形参request和response,形参response指代的就是后端想要返回给前端浏览器的数据,该方法必须返回该形参,也可以替换
	'''如果在执行process_request方法的时候直接返回了HttpResponse对象, 那么会原路返回执行process_response,不是执行所有'''

需要了解:
  1.process_view
  	路由匹配成功之后执行视图函数/类之前自动触发(顺序同process_request)
  2.process_exception
  	视图函数/类执行报错自动触发(顺序同process_response)
  3.process_template_response
  	视图函数/类返回的HttpResponse对象含有render并且对应一个方法的时候自动触发(顺序同process_response)
# 一定要在配置文件中注册中间件才可以生效(就是那七个下边)
posted @ 2023-01-03 19:40  知了了了了  阅读(51)  评论(0编辑  收藏  举报