码迷,mamicode.com
首页 > 其他好文 > 详细

五十一、form组件,钩子函数,cookie,session,

时间:2019-09-28 20:09:28      阅读:100      评论:0      收藏:0      [点我收藏+]

标签:技术   最大   efi   imp   class   action   oval   isp   第一步   

django form 组件
  
注册功能
1.渲染前端标签获取用户输入 》》》》》》 渲染标签
2.获取用户输入船体到后端校验 》》》》》》 校验数据
3.校验未通过展示错误信息 》》》》》》》》 展示信息

校验数据(前后端都可以)
校验前端后端都可以做,但是前端可以不做,后端必须做

django form组件的三大功能
1.渲染标签
2.校验数据
3.展示信息
校验数据:
第一步:写一个form类
 from django import forms
    class MyForm(forms.Form):
        name = forms.CharField(max_length=6, label="用户名")  # 最大为6位,不能超过
        password = forms.CharField(max_length=8, min_length=3, label="密码")  # 字段不能小于3大于8
        email = forms.EmailField(required=False, label="邮箱")  # required=False不做校

第二部: 实例化form对象
form_obj = MyForm({"name":"json","password":"123","email":"123@qq.com"})
   第三部:查看数据校验是否合法
form_obj.is_valid() # 只有所有字段都通过才是True
第四部:查看校验错误的信息
form_obj.errors # 这个放到所有校验未通过的错误信息
第五部:查看通过的信息
form_obj.cleaned_data # 所有校验符合信息

ps: form组件校验数据的规则从上往下一次取值校验
校验通过的放到cleaned_data 中
校验失败的放到form_obj.errors
form 所有字段默认都是必须传值的(required=True),不校验改为false
校验数据时候可以多传,多传的数据不会校验,也不会影响校验结果

渲染标签
form组件只帮你渲染获取用户输入的标签(input),不会帮你渲染提交按钮,需要手动添加

   def register(request):
    # 生成一个空对象,把对象传进去
       form_obj = MyForm()
       return render(request, "register.html", locals()
    <h1>第一种渲染方式</h1>
 {{ form_obj.name }}   {# 只表示name框 #}
 {{ form_obj.as_p}}   {# 把字段表格框全渲染出来 包括名字
 {{ form_obj.as_ul }}  {# 把字段表格框全渲染出来 包括名字,但是手写字母是大写

<h1>第二种渲染方式</h1>
<form action="">
                <p>{{ form_obj.name.label }}:{{ form_obj.name }}</p>
                <p>{{ form_obj.password.label }} :{{ form_obj.password }}</p>
                <p>{{ form_obj.email.label }}:{{ form_obj.email }}</p>
                <input type="submit" value="确认">
            </form>
 <h1>第三种渲染</h1>
                {% for foo in form_obj %}
                    <p>{{ foo.label }}:{{ foo}}
                    </p>  {#  把三个框都渲染出来 foo 就像第一种传的方式#}
       前端取消校验
            <form action="" method="post" novalidate>
            只需要加上novalidate,取消校验

form组件提交数据

  如果数据不合法,页面上会保留输入数据
  在使用form组件对模型表记性数据校验的时候,只需要保证字段一致
  那么在创建的对象的时候你就直接**form_obj.cleaned_data
# 把数据添加到数据库
def register(request):
       # 生成一个空对象,把对象传进去
       form_obj = MyForm()
       if request.method == "POST":
           print(request.POST)
           print(request.POST.get("name"))
           form_obj = MyForm(request.POST)  # 现在变成有值的对象
           # form_obj注意和if上面一样,重新把对象赋值,如果是错误下面不走,然后返回到前端
           if form_obj.is_valid():
               print(form_obj.cleaned_data)  # {‘name‘: ‘json‘, ‘password‘: ‘666‘, ‘email‘: ‘123@qq.com‘}
               models.User.objects.create(**form_obj.cleaned_data)  # 打散后直接创建,不需要挨个获取了
               return HttpResponse("ok")

       return render(request, "register.html", locals())
    前端展示错误信息:
     <form action="" method="post" novalidate>
           {% for foo in form_obj %}
               <p>{{ foo.label }}:{{ foo}}
               <span>{{ foo.errors.0 }}</span> {# 打印错误信息 #}
               </p>  {#  把三个框都渲染出来 foo 就像第一种传的方式#}
           {% endfor %}
           <input type="submit">
       </form>
#校验用户,设置条件
class
MyForm(forms.Form): name = forms.CharField(max_length=6, label="用户名", error_messages={ "mex_length": "用户名最长六位", "required": "用户名不能为空" }) # 最大为6位,不能超过 password = forms.CharField(max_length=8, min_length=3, label="确认密码") # 字段不能小于3大于8 ,确认密码 confirm_password = forms.CharField(max_length=8, min_length=3, label="密码") # 字段不能小于3大于8 email = forms.EmailField(label="邮箱", error_messages={ "required": "邮箱不能为空", "invalid": "邮箱格式不正确" }) # required=False不做校验
# 钩子函数:
  简单说就对于校验通过的字段,再次进行校验
  # 局部钩子函数单个字段的校验利用局面)
    def clean_name(self):
        name = self.cleaned_data.get("name")
        if "666" in name:
            self.add_error("name", "sb666")  # 添加错误
        return name  # return还是要加上,考虑兼容
# 全局钩子
def clean(self):
    password = self.cleaned_data.get("password")
    confirm_password = self.cleaned_data.get("confirm_password")
    if not password == confirm_password:
        self.add_error("password", "两次密码不相等")
    return self.cleaned_data
# 设置标签样式
 from django.forms import widgets
    password = forms.CharField(max_length=8, min_length=3, label="确认密码",widget=widgets.PasswordInput())  密文
    password = forms.CharField(max_length=8, min_length=3, label="确认密码",widget=widgets.PasswordInput(attrs={"class":"form_control c1"}))   样式

#choices字段
gender = forms.ChoiceField(
    choices=((1, ""), (2, ""), (3, "保密")),
    label="性别",
    initial=3, # 默认值
    widget=forms.widgets.RadioSelect()
cookie
保存在客户端浏览器上的键值对

session
保存在服务端上的键值对
服务端产生随机的串返回给客户端,服务端找一个地方将串与对应的信息存起来(随机字符串:敏感信息)

django
return HttpResponse()
return render()
return redirect()

obj = HttpResponse()
return obj
obj = render()
return obj
obj = redirect()
return obj

cookie使用方法
设置cookie
obj.set_cookie("name","json") # 给浏览器设置cookie
获取cookie
request.COOKIE.get("name")
删除
delete_cookie("user")
删除cookie
def logout(request):
rep = redirect("/login/")
rep.delete_cookie("user") # 删除
return rep
cookie装饰器:
技术图片
def login_auth(func):
    @wraps(func)
    def inner(request, *args, **kwargs):
        old_path = request.get_full_path()
        if request.COOKIES.get("name"):
            return func(request, *args, **kwargs)
        return redirect("/login/?next=%s" % old_path)  # 拿到之前访问路径

    return inner


"""1.想要登录之前,登录后返回当前你想要的的界面
   2.在装饰器上,把自己的路劲记录下来get请求
   3.当你登录过后,做一个判断,如果有值直接返回你想返回的界面,
   4.如果没有值,直接跳转到主页面"""


def index(request):
    print(request.COOKIES.get("name"))
    if request.COOKIES.get("name"):
        return HttpResponse("我是index页面,只有登录才能展示")
    return redirect("/login/")


@login_auth
def home(request):
    return HttpResponse("home.去死吧")


@login_auth
def nice(request):
    return HttpResponse("nice,总有刁民想害朕")
装饰器
session
设置session
request.session["name"] = "json"
# 1.先生成一个随机的字符串
# 2.在django session表中存储该随机字符串与数据的记录
# 3.将随机的字符串发送给客户端浏览器
获取session
request.session.get("name")
# 1.django自动获取浏览器字符串 取django session表中里面进行比对
# 2. 如果比对成功 会将当前对应的数据赋值给request.session
# 3. 通过request.session 操作该数据(数据不存在,也不会影响业务逻辑)

当后端执行request.session["name"] = "json",会自动把数据存储到数据库中django_session表中,第一个表示随机的串,
第二个是加密后的键值对,第三个是超时时间默认14天, 浏览器会设置一个键为sessionid来存放session值,只要服务端设置成功,浏览器
也会自动保存
ps:传给客户端的是session值是表中第一个数据,然后进行比对,看是否登录

django默认的session存活的时间是两周14天
一个浏览器占一行

# 删除当前会话的所有Session数据(删除数据库中)
request.session.delete()
  
# 删除当前的会话数据并删除会话的Cookie。(删除两边的)
request.session.flush()

# 设置会话Session和Cookie的超时时间
request.session.set_expiry(value)
* 如果value是个整数,session会在些秒数后失效。
* 如果value是个datatime或timedelta,session就会在这个时间后失效。
* 如果value是0,用户关闭浏览器session就会失效。
* 如果value是None,session会依赖全局session失效策略。
CBV加装饰器
 from django.utils.decorators import method_decorator

    # 类装饰器
    # @method_decorator(login_auth, name="get")  # 第二种方法
    class MyHome(View):
        @method_decorator(login_auth)  # 第三种方法  get和post都会被装饰
        def dispatch(self, request, *args, **kwargs):
            super().dispatch(request, *args, **kwargs)

        # @method_decorator(login_auth)  # 第一种方法
        def get(self, request):
            return HttpResponse("get")

        def post(self, request):
            return HttpResponse("post")

 




五十一、form组件,钩子函数,cookie,session,

标签:技术   最大   efi   imp   class   action   oval   isp   第一步   

原文地址:https://www.cnblogs.com/wukai66/p/11604430.html

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!