首页 > 代码库 > Python之路Day21-自定义分页和cookie

Python之路Day21-自定义分页和cookie

本节知识点概要

1.URL

2.views

        - 请求其他信息

        - 装饰器

3.Templates

          - 母版

           - 自定义

4.Models操作

5.分页(自定义分页)

6.cookie

7.session 

8.Form验证
  - 缓存
  - 中间件
  - 信号
  - CSRF
  - Admin/ModelForm

上节内容回顾

1.请求周期

url> 路由 > 函数或类 > 返回字符串或者模板语言?

form表单提交

提交 -> url路由系统 > 函数或类中的方法 
                 - 执行其他操作,最终返回
                 HttpResponse(....)
                 render(request,index.html)
                 redirect(/index/)
                  返回字符串  >   > 返回给用户
(当接受到redirect时)自动发起另外一个请求
--> url   .....

 Ajax请求

$.ajax({
    url: /index/,
    data: {k: v, list: [1,2,3,4], k3: JSON.stringfy({k1: v}))}, $(form对象).serilize() 
    type: POST,
    dataType: JSON:
    traditional: true,
    success:function(d){
        location.reload()              # 刷新
        location.href = http://www.mamicode.com/"某个地址"      # 跳转
    }
})
提交 -> url -> 函数或类中的方法 
                HttpResponse({})
                render(request, index.html, {name: v1})
                <h1>{{ name }}</h1> --> 
                <h1>v1</h1>
                
                XXXXXXX redirect...
用户    <<<<<  字符串

2.路由系统URL

a. /index/                               ->  函数或类
b. /index/(\d+)                          ->  函数或类
c. /index/(?P<nid>\d+)                   ->  函数或类
d. /index/(?P<nid>\d+) name=root       ->  函数或类
            reverse()
            {% url root 1%}
e. /crm/    include(app01.urls)        -> 路由分发
        
f. 默认值
    url(r^index/, views.index, {name: root}),
            def index(request,name):
                print(name)
                return HttpResponse(OK)
    
g. 命名空间
       /admin/    include(app01.urls,namespace=m1)
            /crm/      include(app01.urls,namespace=m1)
            
        app01.urls
/index/ name = n1
reverser(m1:n1)

3.viwes

def func(request):
    request.POST
    request.GET
    request.FILES
    request.getlist
    request.method
    request.path_info
    
    return render,HttpResponse,redirect

4.模板引擎

render(request, index.html)
# for
# if
# 索引.   keys  values items    all

5.medels

单表
class
User(models.Model): username = models.CharField(max_length=32) email = models.EmailField() 有验证功能 Django Admin 无验证功能: User.objects.create(username=root,email=asdfasdfasdfasdf) User.objects.filter(id=1).update(email=666)
多表:
创建数据库结构
class UserType(models.Model): name = models.CharField(max_length=32) class User(models.Model): username = models.CharField(max_length=32) email = models.EmailField() user_type = models.ForeignKey("UserType")
跨表操作: user_list
= User.objects.all() for obj user_list: obj.username,obj.email,obj.user_type_id,obj.user_type.name,obj.user_type.id //获取单个列表 user = User.objects.get(id=1) user.
//获取指定列内容 User.objects.all().values(
"username","user_type__name",) 多对多 class UserType(models.Model): name = models.CharField(max_length=32) class User(models.Model): username = models.CharField(max_length=32) email = models.EmailField() user_type = models.ForeignKey("UserType") m = models.ManyToMany(UserGroup) class UserGroup(models.Model): name = .... 操作: obj = User.objects.get(id=1) obj.m.add(2) obj.m.add(2,3) obj.m.add(*[1,2,3]) obj.m.remove(...) obj.m.clear() obj.m.set([1,2,3,4,5]) # 多个组,UserGroup对象 obj.m.all() obj.m.filter(name=CTO)

一、views 请求的其他信息

    from django.core.handlers.wsgi import WSGIRequest
    print(type(request))
    print(request.environ)
    for k,v in request.environ.items():
        print(k,v)
    print(request.environ[HTTP_USER_AGENT])

装饰器

FBV

def auth(func):
    def inner(reqeust,*args,**kwargs):
        v = reqeust.COOKIES.get(username111)
        if not v:
            return redirect(/login/)
        return func(reqeust, *args,**kwargs)
    return inner

 

CBV

from django import views
from django.utils.decorators import method_decorator

@method_decorator(auth,name=dispatch)
class Order(views.View):

    # @method_decorator(auth)
    # def dispatch(self, request, *args, **kwargs):
    #     return super(Order,self).dispatch(request, *args, **kwargs)

    # @method_decorator(auth)
    def get(self,reqeust):
        v = reqeust.COOKIES.get(username111)
        return render(reqeust,index.html,{current_user: v})

    def post(self,reqeust):
        v = reqeust.COOKIES.get(username111)
        return render(reqeust,index.html,{current_user: v})

 

二、templates

模板继承

技术分享
<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>{% block title %} {% endblock %}</title>
    <link rel="stylesheet" href=http://www.mamicode.com/"/static/commons.css">
    <style>
        .pg-header{
            height: 48px;
            background-color: #1F78A4;
            color: white;
            font-size: 22px;
            line-height: 48px;

        }
    </style>
    {% block css %} {% endblock %}
</head>
<body>
    <div class="pg-header">管理系统</div>

    {% block content %} {% endblock %}

    <script src=http://www.mamicode.com/"/static/jquery.js"></script>
     {% block js %} {% endblock %}
</body>
</html>
master.html
{% extends ‘master.html %}  //指定继承模板
{% block title %}用户管理{% endblock %}
{% block content %}
        <h1>用户管理</h1>
        <ul>
            {% for i in u %}
                 <li>{{ i }}</li>
            {% endfor %}
        </ul>

    {% for i in u %}
    {% include tag.html %}
    {% endfor %}

{% endblock %}

{% block css %}
    <style>
         body{
             background-color: transparent;
         }
    </style>
{% endblock %}
  {% block js %}
      <script>
      </script>
{% endblock %}

1、模版的执行

模版的创建过程,对于模版,其实就是读取模版(其中嵌套着模版标签),然后将 Model 中获取的数据插入到模版中,最后将信息返回给用户。

技术分享
def current_datetime(request):
    now = datetime.datetime.now()
    html = "<html><body>It is now %s.</body></html>" % now
    return HttpResponse(html)
View Code

 

技术分享
from django import template
t = template.Template(My name is {{ name }}.)
c = template.Context({name: Adrian})
print t.render(c)
View Code
技术分享
import datetime
from django import template
import DjangoDemo.settings
 
now = datetime.datetime.now()
fp = open(settings.BASE_DIR+/templates/Home/Index.html)
t = template.Template(fp.read())
fp.close()
html = t.render(template.Context({current_date: now}))
return HttpResponse(html
View Code
技术分享
from django.template.loader import get_template
from django.template import Context
from django.http import HttpResponse
import datetime
 
def current_datetime(request):
    now = datetime.datetime.now()
    t = get_template(current_datetime.html)
    html = t.render(Context({current_date: now}))
    return HttpResponse(html)
View Code
技术分享
return render_to_response(Account/Login.html,data,context_instance=RequestContext(request))
View Code

2、模版语言

 模板中也有自己的语言,该语言可以实现数据展示

  • {{ item }}
  • {% for item in item_list %}  <a>{{ item }}</a>  {% endfor %}
      forloop.counter
      forloop.first
      forloop.last 
  • {% if ordered_warranty %}  {% else %} {% endif %}
  • 母板:{% block title %}{% endblock %}
    子板:{% extends "base.html" %}
       {% block title %}{% endblock %}
  • 帮助方法:
    {{ item.event_start|date:"Y-m-d H:i:s"}}
    {{ bio|truncatewords:"30" }}
    {{ my_list|first|upper }}
    {{ name|lower }}

3、自定义simple_tag

a、在app中创建templatetags模块

b、创建任意 .py 文件,如:xx.py

#!/usr/bin/env python
#coding:utf-8
from django import template
from django.utils.safestring import mark_safe
   
register = template.Library()
   
@register.simple_tag
def my_simple_time(v1,v2,v3):
    return  v1 + v2 + v3
 
@register.simple_tag
def my_input(id,arg):
    result = "<input type=‘text‘ id=‘%s‘ class=‘%s‘ />" %(id,arg,)
    return mark_safe(result)

 

c、在使用自定义simple_tag的html文件中导入之前创建的 xx.py 文件名

{% load xx %}

d、使用simple_tag

{% my_simple_time 1 2 3%}
{% my_input id_username hide%}

e、在settings中配置当前app,不然django无法找到自定义的simple_tag

INSTALLED_APPS = (
    django.contrib.admin,
    django.contrib.auth,
    django.contrib.contenttypes,
    django.contrib.sessions,
    django.contrib.messages,
    django.contrib.staticfiles,
    app01,
)

缺点:不能作为if条件

优点:参数任意

更多见文档:https://docs.djangoproject.com/en/1.10/ref/templates/language/

4、自定义filter

a. app下创建templatetags目录
b. 任意xxoo.py文件
c. 创建template对象 register
d.

@register.filter
def func(a1,a2)
return "asdfasd"

e. settings中注册APP
f. 顶部 {% load xxoo %}
g. {{ 参数1|函数名:"参数二,参数三" }} {{ 参数1|函数名:数字 }}

缺点:最多两个参数,不能加空格
优点:能作为if条件

三、分页

前端设置为安全

{{page_str|safe }}

 后端设置为安全

    from django.utils.safestring import mark_safe
    page_str="""
            <a href="http://www.mamicode.com/user_list/?p=1">1</a>
            <a href="http://www.mamicode.com/user_list/?p=2">2</a>
            <a href="http://www.mamicode.com/user_list/?p=3">3</a>
    """
    page_str=mark_safe(page_str)

 范例:

技术分享
__author__ = Administrator
from django.utils.safestring import mark_safe


class Page:
    def __init__(self, current_page, data_count, per_page_count=10, pager_num=7):
        self.current_page = current_page
        self.data_count = data_count
        self.per_page_count = per_page_count
        self.pager_num = pager_num
    @property
    def start(self):
        return (self.current_page - 1) * self.per_page_count
    @property
    def end(self):
        return self.current_page * self.per_page_count
    @property
    def total_count(self):
        v, y = divmod(self.data_count, self.per_page_count)
        if y:
            v += 1
        return v

    def page_str(self, base_url):
        page_list = []

        if self.total_count < self.pager_num:
            start_index = 1
            end_index = self.total_count + 1
        else:
            if self.current_page <= (self.pager_num + 1) / 2:
                start_index = 1
                end_index = self.pager_num + 1
            else:
                start_index = self.current_page - (self.pager_num - 1) / 2
                end_index = self.current_page + (self.pager_num + 1) / 2
                if (self.current_page + (self.pager_num - 1) / 2) > self.total_count:
                    end_index = self.total_count + 1
                    start_index = self.total_count - self.pager_num + 1

        if self.current_page == 1:
            prev = <a class="page" href="javascript:void(0);">上一页</a>
        else:
            prev = <a class="page" href="http://www.mamicode.com/%s?p=%s">上一页</a> % (base_url, self.current_page - 1,)
        page_list.append(prev)

        for i in range(int(start_index), int(end_index)):
            if i == self.current_page:
                temp = <a class="page active" href="http://www.mamicode.com/%s?p=%s">%s</a> % (base_url, i, i)
            else:
                temp = <a class="page" href="http://www.mamicode.com/%s?p=%s">%s</a> % (base_url, i, i)
            page_list.append(temp)

        if self.current_page == self.total_count:
            nex = <a class="page" href="javascript:void(0);">下一页</a>
        else:
            nex = <a class="page" href="http://www.mamicode.com/%s?p=%s">下一页</a> % (base_url, self.current_page + 1,)
        page_list.append(nex)

        jump = """
        <input type=‘text‘  /><a onclick=‘jumpTo(this, "%s?p=");‘>GO</a>
        <script>
            function jumpTo(ths,base){
                var val = ths.previousSibling.value;
                location.href = http://www.mamicode.com/base + val;>""" % (base_url,)
        page_list.append(jump)
        page_str = mark_safe("".join(page_list))
        return page_str
View Code
技术分享
from utils import pagination
LIST=[]
for i in range(509):
    LIST.append(i)
def user_list(request):
    current_page = request.GET.get(p, 1)
    current_page = int(current_page)
    page_obj=pagination.Page(current_page,len(LIST),)
    data=LIST[page_obj.start:page_obj.end]
    page_str=page_obj.page_str("/user_list/")
    return  render(request,user_list.html,{li:data,page_str:page_str})
View

 

四、cookie和session

cookie

    相当于浏览器上的一个文件

 技术分享

技术分享
<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title></title>
</head>
<body>
    <form action="/login/" method="POST">
        <input type="text" name="username" placeholder="用户名" />
        <input type="password" name="pwd" placeholder="密码" />
        <input type="submit" />
    </form>
</body>
</html>
login
技术分享
<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title></title>
</head>
<body>
    <h1>欢迎登录:{{ current_user }}</h1>
</body>
</html>
index

 

1、获取Cookie:

request.COOKIES[key]
request.get_signed_cookie(key, default=RAISE_ERROR, salt=‘‘, max_age=None)
    参数:
        default: 默认值
           salt: 加密盐
        max_age: 后台控制过期时间

2、设置Cookie:

rep = HttpResponse(...) 或 rep = render(request, ...)
 
rep.set_cookie(key,value,...)
rep.set_signed_cookie(key,value,salt=加密盐,...)
    参数:
        key,              键
        value=‘‘,         值
        max_age=None,     超时时间
        expires=None,     超时时间(IE requires expires, so set it if hasnt been already.)
        path=/,         Cookie生效的路径,/ 表示根路径,特殊的:跟路径的cookie可以被任何url的页面访问
        domain=None,      Cookie生效的域名
        secure=False,     https传输
        httponly=False    只能http协议传输,无法被JavaScript获取(不是绝对,底层抓包可以获取到也可以被覆盖)

由于cookie保存在客户端的电脑上,所以,JavaScript和jquery也可以操作cookie。

<script src=http://www.mamicode.com//static/js/jquery.cookie.js></script>
$.cookie("list_pager_num", 30,{ path: / });
Session

 

...

 

Python之路Day21-自定义分页和cookie