一 模版
一模版的組成javascript
HTML代碼+邏輯控制代碼css
二 邏輯控制代碼的組成html
1 變量(使用雙大括號來引用變量)java
{{var_name}}python
2 標籤(tag)的使用(使用大括號和百分比的組合來表示使用tag)jquery
{%load staticfiles%}web
3 過濾器(filter)的使用數據庫
{{ship_date|date:"Fj,Y"}},ship_date變量傳給data過濾器,date過濾器經過使用"FJ,Y"這幾個參數來格式化日期數據。"|"表明相似Unix命令中的管道操做。django
三 經常使用標籤bootstrap
1 {%if%} 的使用
可使用你的and,or,not來組織的邏輯。但不容許and和or同時出如今條件語句中。新版本中已經支持了 {%elif%} 這樣的用法。
2 {% for %}的使用
用來循環一個序列, 還可使用reserser關鍵字來進行倒序遍歷,通常能夠先用if語句判斷序列是否爲空,再進行遍歷;還可使用empty關鍵字來進行爲空時的跳轉
3 {%csrf_token%}
用於生成csrf_token的標籤,用於防治跨站攻擊驗證。
注意若是你在view的index裏用的是render_to_response方法,此時標籤因爲沒有上下文的關係因此沒有效果,須要:
或者直接使用render。
其實,這裏是會生成一個input標籤,和其餘表單標籤一塊兒提交給後臺的。
4 {% load %}: 加載標籤庫
5 {% url %}: 引用路由配置的地址
6 {% with %}:用更簡單的變量名替代複雜的變量名
7 {% verbatim %}: 禁止render
{% verbatim %}
{{ hello }}
{% endverbatim %}
四 經常使用過濾器
1 add : 給變量加上相應的值
2 addslashes: 給變量中的引號前加上斜線
3 capfirst : 首字母大寫
4 cut : 從字符串中移除指定的字符
5 date : 格式化日期字符串
6 default : 若是值是False,就替換成設置的默認值,不然就是用原本的值
7 default_if_none:若是值是None,就替換成設置的默認值,不然就使用原本的值
五 模版的包含和繼承
包含:{% include %} 容許在模版中包含其餘模版的內容。
標籤的參數能夠是:模版名稱,變量,字符串
{% include 'nav.html' %}
{% include 'app/nav.html'%}
{% include template_name %}
繼承:本質上說,模版繼承就是先構造一個基礎框架模版,然後在其子模版中對它所包含站點共用部分和定義進行重載。
1 {% block %}
定義塊
2 {% extends %}
繼承父模版
注意:
1 包含和繼承能夠把一些共用的網頁模塊獨立出來,以減小代碼的冗餘。
2 若是在模塊裏使用{% extends %}d的話,這個標籤必須在全部模版標籤的最前面,不然模版繼承不工做。
3 一般儘量模版裏的{% block %}越多越好,子模版沒必要定義全部的父block
4 若是你須要父模版的塊內容,{{block.super}}變量能夠幫你完成工做,當你須要爲父塊添加內容而不是取代它的時候這就頗有用。
5 不能在同一模版(不管是父模版仍是子模版)裏定義多個同名{% block %} ,由於塊標籤同時在兩個地方工做,不只在子模版中,並且在父模版中也填充內容,若是子模版有兩個同名的標籤,父模版將不能決定使用哪個塊內容來使用。
二 admin的配置
django admin是django自帶的一個後臺app,提供了後臺的管理功能。
基礎知識點:
一 認識ModelAdmin
管理界面的定製類,如需擴展特定的model界面需從該類繼承
二 註冊medel類到admin的兩種方式:
1 使用register的方法
2 使用register的裝飾器
三 掌握一些經常使用的設置技巧
list_display: 指定要顯示的字段
search_fields:指定搜索的字段
list_filter: 指定列表過濾器
ordering:指定排序字段
三 Form
一 什麼是Form?什麼是DjangoForm?
Django表單系統中,全部的表單類都做爲django.forms.Form的子類建立,包括ModelForm
關於django的表單系統,主要分兩種
基於django.forms.Form:全部表單類的父類
基於django.forms.ModelForm:能夠和模型類綁定的Form
實例:實現添加出版社信息的功能
二 不使用Django Form的狀況
三 使用Form的狀況
首先,在app01中創建forms.py


######################################################### #app01下新建的forms.py from django import forms class Mypub_form(forms.Form): name = forms.CharField(label='名稱',error_messages={'required':'必填'}) address = forms.CharField(label='地址',error_messages={'required':'必填'}) city = forms.CharField(label='城市',error_messages={'required':'必填'}) state_province = forms.CharField(label='省份',error_messages={'required':'必填'}) country = forms.CharField(label='國家',error_messages={'required':'必填'}) website = forms.URLField(label='網址',error_messages={'required':'必填'}) ####################################################### #app01.views def add_publisher(req): if req.method=='POST': # #不使用django form # print(req.POST) # name=req.POST['name'] # address=req.POST.get('address') # city=req.POST['city'] # province=req.POST['province'] # country=req.POST['country'] # website=req.POST['website'] # Publisher.objects.create( # name=name, # city=city, # address=address, # state_province=province, # country=country, # website=website # ) # return HttpResponse("添加出版社信息成功!") #使用django form的狀況 Mypub_form_obj=Mypub_form(req.POST) if Mypub_form_obj.is_valid(): Publisher.objects.create( name=Mypub_form_obj.cleaned_data["name"], address=Mypub_form_obj.cleaned_data["address"], city=Mypub_form_obj.cleaned_data["city"], state_province=Mypub_form_obj.cleaned_data["state_province"], country=Mypub_form_obj.cleaned_data["country"], website=Mypub_form_obj.cleaned_data["website"], ) return HttpResponse("添加出版社信息成功!") else: Mypub_form_obj=Mypub_form() return render(req,'add_publisher.html',locals()) ####################################################### #add_publisher.html <body> <form action="{% url 'add_pub' %}" method="post"> {% csrf_token %} {# 名稱:<input type="text" name="name"><br>#} {# 地址:<input type="text" name="address"><br>#} {# 城市:<input type="text" name="city"><br>#} {# 省份:<input type="text" name="province"><br>#} {# 國家:<input type="text" name="country"><br>#} {# 網址:<input type="text" name="website"><br>#} {# <input type="submit" value="提交"><br>#} {{ Mypub_form_obj.as_p }} <input type="submit" value="提交"><br> </form> </body>
四 使用ModelForm的狀況


####################################################### #app01.views def add_publisher(req): if req.method=='POST': # #不使用django form # print(req.POST) # name=req.POST['name'] # address=req.POST.get('address') # city=req.POST['city'] # province=req.POST['province'] # country=req.POST['country'] # website=req.POST['website'] # Publisher.objects.create( # name=name, # city=city, # address=address, # state_province=province, # country=country, # website=website # ) # return HttpResponse("添加出版社信息成功!") #使用django form的狀況 Mypub_form_obj=Mypub_form(req.POST) if Mypub_form_obj.is_valid(): # Publisher.objects.create( # name=Mypub_form_obj.cleaned_data["name"], # address=Mypub_form_obj.cleaned_data["address"], # city=Mypub_form_obj.cleaned_data["city"], # state_province=Mypub_form_obj.cleaned_data["state_province"], # country=Mypub_form_obj.cleaned_data["country"], # website=Mypub_form_obj.cleaned_data["website"], # ) Mypub_form_obj.save() return HttpResponse("添加出版社信息成功!") else: Mypub_form_obj=Mypub_form() return render(req,'add_publisher.html',locals()) ####################################################### #add_publisher.html <body> <form action="{% url 'add_pub' %}" method="post"> {% csrf_token %} {# 名稱:<input type="text" name="name"><br>#} {# 地址:<input type="text" name="address"><br>#} {# 城市:<input type="text" name="city"><br>#} {# 省份:<input type="text" name="province"><br>#} {# 國家:<input type="text" name="country"><br>#} {# 網址:<input type="text" name="website"><br>#} {# <input type="submit" value="提交"><br>#} {{ Mypub_form_obj.as_p }} <input type="submit" value="提交"><br> </form> </body>
思考:爲何有的顯示漢子,有的顯示英文
總結:
使用Django中Form能夠大大簡化代碼,經常使用的表單功能特性都整合到了Form中,而ModelForm能夠和Model進行綁定,更進一步簡化操做。
四 Form 驗證
django提供了3種方式來驗證表單
實例:自定義驗證,不能插入重名的出版社名稱。
一 表單字段的驗證器
二 clean_filedname,驗證字段,針對某個字段進行驗證。
三 表單clean方法,可針對整個表單進行驗證
像註冊時須要輸入兩次密碼的驗證,用clean來作就很是好,由於前兩種都只是針對某一個字段進行驗證,而確認密碼則須要將兩個字段信息都拿來進行匹配。
五 cookie和session
一、cookie不屬於http協議範圍,因爲http協議沒法保持狀態,但實際狀況,咱們卻又須要「保持狀態」,所以cookie就是在這樣一個場景下誕生。
cookie的工做原理是:由服務器產生內容,瀏覽器收到請求後保存在本地;當瀏覽器再次訪問時,瀏覽器會自動帶上cookie,這樣服務器就能經過cookie的內容來判斷這個是「誰」了。
二、cookie雖然在必定程度上解決了「保持狀態」的需求,可是因爲cookie自己最大支持4096字節,以及cookie自己保存在客戶端,可能被攔截或竊取,所以就須要有一種新的東西,它能支持更多的字節,而且他保存在服務器,有較高的安全性。這就是session。
問題來了,基於http協議的無狀態特徵,服務器根本就不知道訪問者是「誰」。那麼上述的cookie就起到橋接的做用。
咱們能夠給每一個客戶端的cookie分配一個惟一的id,這樣用戶在訪問時,經過cookie,服務器就知道來的人是「誰」。而後咱們再根據不一樣的cookie的id,在服務器上保存一段時間的私密資料,如「帳號密碼」等等。
三、總結而言:cookie彌補了http無狀態的不足,讓服務器知道來的人是「誰」;可是cookie以文本的形式保存在本地,自身安全性較差;因此咱們就經過cookie識別不一樣的用戶,對應的在session裏保存私密的信息以及超過4096字節的文本。
四、另外,上述所說的cookie和session實際上是共通性的東西,不限於語言和框架
前幾節的介紹中咱們已經有能力製做一個登錄頁面,在驗證了用戶名和密碼的正確性後跳轉到後臺的頁面。可是測試後也發現,若是繞過登錄頁面。直接輸入後臺的url地址也能夠直接訪問的。這個顯然是不合理的。其實咱們缺失的就是cookie和session配合的驗證。有了這個驗證過程,咱們就能夠實現和其餘網站同樣必須登陸才能進入後臺頁面了。
先說一下這種認證的機制。每當咱們使用一款瀏覽器訪問一個登錄頁面的時候,一旦咱們經過了認證。服務器端就會發送一組隨機惟一的字符串(假設是123abc)到瀏覽器端,這個被存儲在瀏覽端的東西就叫cookie。而服務器端也會本身存儲一下用戶當前的狀態,好比login=true,username=hahaha之類的用戶信息。可是這種存儲是以字典形式存儲的,字典的惟一key就是剛纔發給用戶的惟一的cookie值。那麼若是在服務器端查看session信息的話,理論上就會看到以下樣子的字典
{'123abc':{'login':true,'username:hahaha'}}
由於每一個cookie都是惟一的,因此咱們在電腦上換個瀏覽器再登錄同一個網站也須要再次驗證。那麼爲何說咱們只是理論上看到這樣子的字典呢?由於處於安全性的考慮,其實對於上面那個大字典不光key值123abc是被加密的,value值{'login':true,'username:hahaha'}在服務器端也是同樣被加密的。因此咱們服務器上就算打開session信息看到的也是相似與如下樣子的東西
{'123abc':dasdasdasd1231231da1231231}
借用一張別的大神畫的圖,能夠更直觀的看出來cookie和session的關係
知道了原理,咱們下面就來用代碼實現
先在templates目錄下建立兩個html,login.html負責登陸頁面。backend頁面表明後臺頁面
login.html
<!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <title>login</title> <link rel="stylesheet" href="http://830909.blog.51cto.com/static/plugins/bootstrap-3.3.5-dist/css/bootstrap.min.css"> </head> <body> <div class="container"> <form action="login.html" method="post"> <div class="form-group"> <label class="sr-only">username</label> <input type="text" class="form-control" name="username" placeholder="用戶名"/> </div> <div class="form-group"> <label class="sr-only">Password</label> <input type="password" class="form-control" name="passwd" placeholder="密碼"/> </div> <div class="form-group"> <input class="btn btn-primary" type="submit" value="http://830909.blog.51cto.com/8311014/Submit"> </div> </form> </div> <script type="application/Javascript" src="http://830909.blog.51cto.com/static/js/jquery-2.2.1.min.js"></script> <script type="application/javascript" src="http://830909.blog.51cto.com/static/plugins/bootstrap-3.3.5-dist/js/bootstrap.min.js"></script> </body> </html>
backend.html
<!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <title>backend</title> <link rel="stylesheet" href="http://830909.blog.51cto.com/static/plugins/bootstrap-3.3.5-dist/css/bootstrap.min.css"> <link rel="stylesheet" href="http://830909.blog.51cto.com/static/css/commons.css"> </head> <body> <div class="container"> <h2>cookie 內容是 {{ cookie_content }}</h2> <h2>session 內容是 {{ session_content }}</h2> <h2>登陸用戶名 :{{ username }}</h2> <a href="http://830909.blog.51cto.com/logout/">註銷</a> </div> <script type="application/javascript" src="http://830909.blog.51cto.com/static/js/jquery-2.2.1.min.js"></script> <script type="application/javascript" src="http://830909.blog.51cto.com/static/plugins/bootstrap-3.3.5-dist/js/bootstrap.min.js"></script> </body> </html>
第二步 編輯app01應用下的views.py文件,編寫代碼邏輯部分
views.py
# /usr/bin/env python # coding:utf-8 from django.shortcuts import render from django.shortcuts import redirect def login(request): if request.method=="POST": username=request.POST['username'] pwd=request.POST['passwd'] if username=='abc' and pwd=='123': #設置session內部的字典內容 request.session['is_login']='true' request.session['username']='abc' #登陸成功就將url重定向到後臺的url return redirect('/backend/') #登陸不成功或第一訪問就停留在登陸頁面 return render(request,'login.html') def backend(request): """ 這裏必須用讀取字典的get()方法把is_login的value缺省設置爲False, 當用戶訪問backend這個url先嚐試獲取這個瀏覽器對應的session中的 is_login的值。若是對方登陸成功的話,在login裏就已經把is_login 的值修改成了True,反之這個值就是False的 """ is_login=request.session.get('is_login',False) #若是爲真,就說明用戶是正常登錄的 if is_login: #獲取字典的內容並傳入頁面文件 cookie_content=request.COOKIES session_content=request.session username=request.session['username'] return render(request,'backend.html', { 'cookie_content':cookie_content, 'session_content':session_content, 'username':username }) else: """ 若是訪問的時候沒有攜帶正確的session, 就直接被重定向url回login頁面 """ return redirect('/login/') def logout(request): """ 直接經過request.session['is_login']回去返回的時候, 若是is_login對應的value值不存在會致使程序異常。因此 須要作異常處理 """ try: #刪除is_login對應的value值 del request.session['is_login'] except KeyError: pass #點擊註銷以後,直接重定向回登陸頁面 return redirect('/login/')
第三步,編輯mydjango目錄下的urls.py文件。設置函數與頁面的綁定關係
urls.py
from django.conf.urls import url from django.contrib import admin from app01 import views urlpatterns = [ url(r'^admin/', admin.site.urls), url(r'^login/', views.login), url(r'^backend/', views.backend), url(r'^logout/', views.logout), ]
最後打開瀏覽器直接訪問/backend/頁面的時候直接就被重定向到了/login/
只有在輸入了正確的用戶名和密碼以後才進入到了/backend/頁面
從上圖中咱們看到有一下幾點:
一、login頁面正確登陸的話,後臺頁面能夠獲取到瀏覽器攜帶的cookie的。
二、第一行的sessionid其實就是cookie值
三、session的內容是加密的,從客戶端獲取不到session的內容
四、服務端能夠經過預設的key值取出session的內容並打印到前段
從火狐瀏覽器裏查看cookie
django的session默認是存儲在數據庫裏的,咱們再到數據庫查看一下真正session內容
下面咱們再來最後的總結一下cookie和session的知識點
1、操做Cookie
獲取cookie:request.COOKIES[key]
設置cookie:response.set_cookie(key,value)
因爲cookie保存在客戶端的電腦上,因此,jquery也能夠操做cookie。
<script src='http://830909.blog.51cto.com/static/js/jquery.cookie.js'></script> $.cookie("list_pager_num", 30,{ path: '/' });
2、操做Session(session默認在服務器端保存15天)
獲取session:request.session[key]
設置session:reqeust.session[key] = value
刪除session:del request.session[key]
(這個刪除其實就是把數據庫的session_data更新爲一個其餘的值了,並無當即刪除)
request.session.set_expiry(value) * 若是value是個整數,session會在些秒數後失效。 * 若是value是個datatime或timedelta,session就會在這個時間後失效。 * 若是value是0,用戶關閉瀏覽器session就會失效。 * 若是value是None,session會依賴全局session失效策略。
參考: http://www.07net01.com/2016/03/1364624.html