django

http://docs.30c.org/djangobook2css

MVC 设计模式

首先,咱们分红4个Python的文件,(models.py ,views.py , urls.py ) 和html模板文件 (latest_books.html )html

  • models.py 文件主要用一个 Python 类来描述数据表。 称为 模型(model) 。 运用这个类,你能够经过简单的 Python 的代码来建立、检索、更新、删除 数据库中的记录而无需写一条又一条的SQL语句。python

  • views.py文件包含了页面的业务逻辑。 latest_books()函数叫作视图mysql

  • urls.py 指出了什么样的 URL 调用什么的视图。 在这个例子中 /latest/ URL 将会调用 latest_books()这个函数。 换句话说,若是你的域名是example.com,任何人浏览网址http://example.com/latest/将会调用latest_books()这个函数。jquery

  • latest_books.html 是 html 模板,它描述了这个页面的设计是如何的。 使用带基本逻辑声明的模板语言,如{% for book in book_list %}nginx

结合起来,这些部分松散遵循的模式称为模型-视图-控制器(MVC)。 简单的说, MVC 是一种软件开发的方法,它把代码的定义和数据访问的方法(模型)与请求逻辑 (控制器)还有用户接口(视图)分开来。sql

Django 里更关注的是模型(Model)、模板(Template)和视图(Views),Django 也被称为 MTV 框架 。在 MTV 开发模式中:数据库

  • M 表明模型(Model),即数据存取层。 该层处理与数据相关的全部事务: 如何存取、如何验证有效性、包含哪些行为以及数据之间的关系等。django

  • T 表明模板(Template),即表现层。 该层处理与表现相关的决定: 如何在页面或其余类型文档中进行显示。centos

  • V 表明视图(View),即业务逻辑层。 该层包含存取模型及调取恰当模板的相关逻辑。 你能够把它看做模型与模板之间的桥梁。

Django基本配置

  Python的WEB框架有Django、Tornado、Flask 等多种,Django相较与其余WEB框架其优点为:大而全,框架自己集成了ORM、模型绑定、模板引擎、缓存、Session等诸多功能

一、安装:
  方式1、pip3 install django
  方式2、官网下载
      解压
      python3 setup.py install

# 添加环境变量 C:\Python3\Scripts


二、基本操做:

  • 建立project

    先进入本身指定的目录
    django-admin startproject mysite
  

 

  • 建立app
  cd mysite

  python3 manage.py startapp cmdb

  python3 manage.py startapp monitor

 

  mysite对应的目录结构

  - mysite (配置文件)

    -init

    -settings 配置文件

    -urls URL对应关系

    -wsgi  遵循WSIG规范,uwsgi+nginx

  - manage.py (管理Project)
  - app(cmdb)
    - models.py 数据库操做
    - admin.py 配置Django自带的后台管理
    - apps.py 当前app的配置
    - tests.py 单元测试
    - views.py 作业务处理...

Django里面没封装socket,当进行socket数据交互时要用到wsgi,生产环境下通常用第三方模块uwsgi和nginx就能够把Django程序跑起来

  • 建立templates目录

    放html文件

    须要在settings.py中加上

'DIRS': [os.path.join(BASE_DIR,'templates')],

 

  • 编辑url.py view.py 

    url是路由系统,每一个url对应view函数处理业务

    view.py  业务处理

      一、return render(request,模板路径,{'key':'value'})   

      二、return redirect(url) 跳转

      三、return HttpResponse('ok')

  • 运行
  cd mysite
  python3 manage.py runserver 127.0.0.1:8000

 

1.urls.py下面指定url,一个url对应一个函数 from cmdb import view

2.view.py下面写函数,return的html会去templates目录下找

3.settings.py指定了html在templates目录下,若是POST的方式发送,这行须要注释,不然forbidden

# 'django.middleware.csrf.CsrfViewMiddleware',

 用户在浏览器中输入url,看到页面展现,整个流程

  url.py中匹配对应的路由系统,去view.py中找对应的函数处理,默认method=get,返回templates中的html。

 静态文件(css,js,图片)

建立statics文件夹(文件夹名字随意)

settings.py最后加上

STATIC_URL = '/static/'

STATICFILES_DIRS = (
    os.path.join(BASE_DIR,'statics'),#这里面的路径必定是建立的文件
os.path.join(BASE_DIR,'static'),#若是statics和static下面都有相同的js,优先执行statics的,static下面的不执行 )

css

建立commons.css

<link rel="stylesheet" href="/static/commons.css">

js

建立commons.js,记得把jquery也放在此目录下

{% load staticfiles %}#放在html最上面

<script src="{% static "jquery-1.12.4.js" %}"></script>
<script src="{% static "commons.js"%}"></script>

 

django数据库操做

  类 --> 数据库的表

  字段 --> 列

  对象 --> 一行数据

建立数据库表sqlite

models.py

        class UserInfo(models.Model):
            nid = models.AutoField(primary_key=True)
       user_group = models.ForeignKey('UserGroup') username
= models.CharField(max_length=32) pwd = models.CharField(max_length=64) age = models.IntegerField()
     class UserGroup(models.Model):
       uid = models.AutoField(primary_key=True)
       caption = models.CharField(max_length=64)

*须要在settings.py下  INSTALLED_APPS加上app名字,不然不能建立表

termail下执行

  python3 manage.py makemigrations

  python3 manage.py migrate

须要注意的是,在建立完数据库后,UserInfo表中会出现user_group_id的字段,user_group存在的,表明UserGroup这个对象

在view.py中,能经过user_group访问对象的属性

obj = models.UserInfo.objects.all()

for row in obj:

  row.user_group.uid

  row.user_group.caption

链接mysql

*须要本身先建立数据库

create database day19 charset utf8;

*django链接mysql用的是MySqlDB,若是用的是python3的话,须要在配置目录的init.py中加上:

import pymysql
pymysql.install_as_MySQLdb()

settings.py

DATABASES = {
    'default': {
        'ENGINE': 'django.db.backends.mysql',
        'NAME': 'day19',
        'USER': 'root',
        'PASSWORD': 'centos',
        'HOST': '192.168.147.147',
        'PORT': '3306',
    }
}

数据库基本操做

a. 查

  models.tb.objects.all()
  models.tb.objects.filter(nid=1)
  models.tb.objects.filter(nid=1).first()

b. 增
  1.models.tb.objects.create(...)
  2.
  obj = models.tb(...)
  obj.save()
c. 删
  models.tb.objects.all().delete()
  models.tb.objects.filter(nid=1).delete()
d. 改
  models.tb.objects.all().update(...)
  models.tb.objects.filter(nid=1).update(...)

路由系统urls.py

一、单一路由对应

1
url(r '^index$' , views.index),

二、基于正则的路由

1
2
url(r '^index/(\d*)' , views.index),
url(r '^manage/(?P<name>\w*)/(?P<id>\d*)' , views.manage),

利用  url(r'^edit_user_new-(?P<nnid>\d+).html$', views.edit_user_new)实现编辑,url中带.html觉得是静态文件,权重会高点。

整个流程  

  user.html中<a href="/edit_user_new-{{ row.nid }}.html">新编辑</a>

  新编辑跳转到这个url,url.py中加url(r'^edit_user_new-(?P<nnid>\d+).html$', views.edit_user_new)

  views.py中def edit_user_new(request,nnid)须要带上参数,method是GET

  编辑完以后提交,action="/edit_user_new-{{ obj.nid }}.html"

  

三、添加额外的参数

1
url(r '^manage/(?P<name>\w*)' , views.manage,{ 'id' : 333 }),

四、为路由映射设置别名

1
2
url(r '^home' , views.home, name = 'h1' ),
url(r '^index/(\d*)' , views.index, name = 'h2' ),

h1就代指这个url

<form method="POST" action="{% url 'nnn' nnid=obj.nid %}">

设置名称以后,能够在不一样的地方调用,如:

  • 模板中使用生成URL     {% url 'h2' 2012 %}
  • 函数中使用生成URL     reverse('h2', args=(2012,))      路径:django.urls.reverse
  • Model中使用获取URL  自定义get_absolute_url() 方法

五、根据app对路由规则进行分类

1
url(r '^app01/' ,include( 'app01.urls' )),

当访问127.0.0.1:8000/app01/user时,先去匹配前面的app01,而后去app01下面的url.py中匹配

六、命名空间

a. project.urls.py

1
2
3
4
5
6
from  django.conf.urls  import  url,include
 
urlpatterns  =  [
     url(r '^a/' , include( 'app01.urls' , namespace = 'author-polls' )),
     url(r '^b/' , include( 'app01.urls' , namespace = 'publisher-polls' )),
]

b. app01.urls.py

1
2
3
4
5
6
7
from  django.conf.urls  import  url
from  app01  import  views
 
app_name  =  'app01'
urlpatterns  =  [
     url(r '^(?P<pk>\d+)/$' , views.detail, name = 'detail' )
]

c. app01.views.py

1
2
3
def  detail(request, pk):
     print (request.resolver_match)
     return  HttpResponse(pk)

以上定义带命名空间的url以后,使用name生成URL时候,应该以下:

  • v = reverse('author-polls:detail', kwargs={'pk':11})
  • {% url 'app01:detail' pk=12 pp=99 %}

django中的路由系统和其余语言的框架有所不一样,在django中每个请求的url都要有一条路由映射,这样才能将请求交给对一个的view中的函数去处理。其余大部分的Web框架则是对一类的url请求作一条路由映射,从而是路由系统变得简洁。

视图函数views.py

  获取请求信息:
    request.POST {'username':'root'..}
    request.GET
    request.FILES

      obj = request.FILES.get(input里面的name)

      文件名 obj.name

      for line in obj.chunks()

    request.method
    request.body = username=root;age=18;gender=male

  响应结果:
    return HttpReponse(..)
    return render(request,'path/a.html',{})
    return redirect('http://www.baidu.com')

模板

 模板中也有本身的语言,该语言能够实现数据展现

  • {{ item }}
  • {% for item in item_list %}  <a>{{ item }}</a>  {% endfor %}
      forloop.counter
      forloop.first
      forloop.last 
  • {% if ordered_warranty %}  {% else %} {% endif %}
  • extend

    母板:{% block title %}{% endblock %}
    子板:{% extends "base.html" %}
       {% block title %}新内容{% endblock %}

  • include

    子板:{% extends "base.html" %}
       {% block title %}新内容{%include 'small.html'%}{% endblock %} 

  • 字典.key   列表.索引
  • 帮助方法:
    {{ item.event_start|date:"Y-m-d H:i:s"}}
    {{ bio|truncatewords:"30" }}
    {{ my_list|first|upper }}
    {{ name|lower }}

三、自定义simple_tag(页面展现)

a、在app中建立templatetags模块

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

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
#!/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)
from django import template
from django.utils.safestring import mark_safe
register = template.Library()

@register.filter()

def anyway(value,num):
    return 'dassssssssssssssssssssssssssss'+value+str(num)
@register.filter()
def ya(value,v):
    temp = "<a href='http://www.baidu.com?t=%s'>%s</a>"%(v,value)
    return mark_safe(temp)

 

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

1
{ %  load xx  % }

d、使用simple_tag

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

e、在settings中配置当前app,否则django没法找到自定义的simple_tag  

1
2
3
4
5
6
7
8
9
INSTALLED_APPS  =  (
     'django.contrib.admin' ,
     'django.contrib.auth' ,
     'django.contrib.contenttypes' ,
     'django.contrib.sessions' ,
     'django.contrib.messages' ,
     'django.contrib.staticfiles' ,
     'app01' ,
)

四、自定义filter(在if条件中作条件时)

{{ summary|anyway:8 }}

在页面仅显示内容用simple_tag

 cookie

  - 是用户浏览器上的一个键值对
  - 设置超时时间

  利用cookie可实现:
    - 登陆验证
    - 页面显示条数
    - 拖动位置..

  两大忌讳:
    - 敏感信息
    - 简单

一、获取Cookie:

1
2
3
4
5
6
request.COOKIES.get( 'key')
request.get_signed_cookie(key, default = RAISE_ERROR, salt = '', max_age = None )
     参数:
         default: 默认值
            salt: 加密盐
         max_age: 后台控制过时时间

二、设置Cookie:

1
2
3
4
5
6
7
8
9
10
11
12
13
rep  =  HttpResponse(...) 或 rep = render(request, ...) 或 rep = redirect(url)
 
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  hasn't been already.)
         path = '/' ,         Cookie生效的路径, /  表示根路径,特殊的:跟路径的cookie能够被任何url的页面访问
         domain = None ,      Cookie生效的域名
         secure = False ,     https传输
         httponly = False     只能http协议传输,没法被JavaScript获取(不是绝对,底层抓包能够获取到也能够被覆盖)

因为cookie保存在客户端的电脑上,因此,JavaScript和jquery也能够操做cookie。

1
2
<script src = '/static/js/jquery.cookie.js' >< / script>
$.cookie( "list_pager_num" 30 ,{ path:  '/'  });

  设置cookie

    obj = redirect('/app02/groups')
    obj.set_cookie(key='user_name',value=u,max_age=10)
    return obj

  获取cookie

    request.COOKIES.get('user_name')

session

session依赖cookie

SESSION_ENGINE = 'django.contrib.sessions.backends.db'  # 引擎(默认)

SESSION_COOKIE_NAME = "sessionid" # Session的cookie保存在浏览器上时的key,即:sessionid=随机字符串(默认)
SESSION_COOKIE_PATH = "/" # Session的cookie保存的路径(默认)
SESSION_COOKIE_DOMAIN = None # Session的cookie保存的域名(默认)
SESSION_COOKIE_SECURE = False # 是否Https传输cookie(默认)
SESSION_COOKIE_HTTPONLY = True # 是否Session的cookie只支持http传输(默认)
SESSION_COOKIE_AGE = 1209600 # Session的cookie失效日期(2周)(默认)
SESSION_EXPIRE_AT_BROWSER_CLOSE = False # 是否关闭浏览器使得Session过时(默认)
SESSION_SAVE_EVERY_REQUEST = False

 生成随机字符串保存在客户端,服务器端保存形式字典,{'随机字符串':{'username':'root','password':'pwd'}}

  request.session['user'] = u

  v = request.session.get('user')

装饰器+session实现登陆认证

from django.shortcuts import render
from django.shortcuts import redirect
from django.shortcuts import HttpResponse

from app01 import models
# Create your views here.
def auth(func):
    def inner(request,*args,**kwargs):
        v = request.session.get('user')
        if not v:
            return redirect('/app02/login')
        else:
            return func(request,*args,**kwargs)
    return inner
@auth
# group = auth(group)
def group(request):
    # # v = request.session.get('username')
    # if not v:
    #     return redirect('/app02/login')
    # else:
    return render(request,'groups.html')
@auth
def user(request):
    return render(request,'user.html')

def login(request):
    if request.method == 'GET':
        return render(request,'login.html')
    elif request.method == 'POST':
        u = request.POST.get('username')
        p = request.POST.get('pwd')
        v = models.UserInfo.objects.filter(username=u,pwd=p).first()
        if v:
            obj = redirect('/app02/groups')
            # obj.set_cookie(key='user',value=u,max_age=10)
            request.session['user'] = u
            return obj
        else:
            return render(request, 'login.html',{'msg':'用户名或密码错误'})

主要加了个auth函数,auth函数功能,取session,有执行func,没有的话跳转到login

相关文章
相关标签/搜索