https://www.cnblogs.com/pandaboy1123/p/9894981.htmljavascript
HTTP協議是Hyper Text Transfer Protocol(超文本傳輸協議)的縮寫,是用於萬維網(WWW:World Wide Web )服務器與本地瀏覽器之間傳輸超文本的傳送協議。php
瀏覽器做爲HTTP客戶端經過URL向HTTP服務端即WEB服務器發送全部請求。Web服務器根據接收到的請求後,向客戶端發送響應信息。html
url:統一資源定位符 ,是互聯網上標準資源的地址。前端
HTTP定義了與服務器交互的8種 請求方式java
列舉Http請求中常見的請求方式
根據HTTP標準,HTTP請求可使用多種請求方法。
HTTP1.0定義了三種請求方法: GET, POST 和 HEAD方法。
HTTP1.1新增了五種請求方法:OPTIONS, PUT, DELETE, TRACE 和 CONNECT 方法
----------------------------------------------------------------
get 和 post區別python
區別:nginx
get請求無消息體,只能攜帶少許數據git
post請求有消息體,能夠攜帶大量數據web
攜帶數據的方式:ajax
get請求將數據放在url地址中
post請求將數據放在消息體中
GET請求請提交的數據放置在HTTP請求協議頭中,而POST提交的數據則放在實體數據中;
GET方式提交的數據最多隻能有1024字節,而POST則沒有此限制。
http協議是基於網絡應用層的,對服務器和客戶端(瀏覽器)之間的一種傳輸超文本的傳送協議
長鏈接:HTTP的相應頭內有Connection:keep-alive 在使用長鏈接的狀況下,當一個網頁打開完成後,客戶端和服務器之間用於傳輸HTTP數據的 TCP鏈接不會關閉,若是客戶端再次訪問這個服務器上的網頁,會繼續使用這一條已經創建的鏈接。
Keep-Alive不會永久保持鏈接,它有一個保持時間,能夠在不一樣的服務器軟件(如Apache)中設定這個時間。實現長鏈接要客戶端和服務端都支持長鏈接。 HTTP協議的長鏈接和短鏈接,實質上是TCP協議的長鏈接和短鏈接
http協議特色
一、基於TCP/IP
二、基於請求-響應模式-->請求從客戶端發出,最後服務器端響應該請求並 返回
三、無狀態保存---不對請求和響應之間的通訊狀態進行保存
四、無鏈接---每次鏈接只處理一個請求。服務器處理完客戶的請求,並收到客戶的應答後,即斷開鏈接。採用這種方式能夠節省傳輸時間。
MVC
Web服務器開發領域裏著名的MVC模式,所謂MVC就是把Web應用分爲模型(M),控制器(C)和視圖(V)三層,他們之間以一種插件式的、鬆耦合的方式鏈接在一塊兒
模型負責業務對象與數據庫的映射(ORM),視圖負責與用戶的交互(頁面),控制器接受用戶的輸入調用模型和視圖完成用戶的請求,其示意圖以下所示:
MTV
Django的MTV模式本質上和MVC是同樣的,也是爲了各組件間保持鬆耦合關係,只是定義上有些許不一樣,Django的MTV分別是值:
model 英 /'mɒdl/ 美 /'mɑdl/
通常是用戶經過瀏覽器向咱們的服務器發起一個請求(request),這個請求會去訪問視圖函數,(若是不涉及到數據調用,那麼這個時候視圖函數返回一個模板也就是一個網頁給用戶),
視圖函數調用模型,模型去數據庫查找數據,而後逐級返回,視圖函數把返回的數據填充到模板中空格中,最後返回網頁給用戶。
Django的請求生命週期是指當用戶在瀏覽器上輸入url到用戶看到網頁的這個時間段內,Django後臺所發生的事情
通常是用戶經過瀏覽器向咱們的服務器發起一個請求(request),這個請求會去訪問視圖函數,(若是不涉及到數據調用,那麼這個時候視圖函數返回一個模板也就是一個網頁給用戶),
視圖函數調用模型,模型去數據庫查找數據,而後逐級返回,視圖函數把返回的數據填充到模板中空格中,最後返回網頁給用戶。
#1.wsgi,請求封裝後交給web框架 (Flask、Django) #2.中間件,對請求進行校驗或在請求對象中添加其餘相關數據,例如:csrf、request.session - #3.路由匹配 根據瀏覽器發送的不一樣url去匹配不一樣的視圖函數 #4.視圖函數,在視圖函數中進行業務邏輯的處理,可能涉及到:orm、templates => 渲染 - #5.中間件,對響應的數據進行處理。 #6.wsgi,將響應的內容發送給瀏覽器。
五、簡述什麼事FBV和CBV
FBV(function base views) 就是在視圖裏使用函數處理請求 CBV(class base views) 就是在視圖裏使用類處理請求
Python是一個面向對象的編程語言,若是隻用函數來開發,有不少面向對象的優勢就錯失了(繼承、封裝、多態)。
因此Django在後來加入了Class-Based-View。可讓咱們用類寫View。這樣作的優勢主要下面兩種: 提升了代碼的複用性,可使用面嚮對象的技術,好比Mixin(多繼承) 能夠用不一樣的函數針對不一樣的HTTP方法處理,而不是經過不少if判斷,提升代碼可讀性
object relation map
首先在視圖模塊中添加如下導入 from rest_framework import permissions
中間件顧名思義,是介於request與response處理之間的一道處理過程,相對比較輕量級,而且在全局上改變django的輸入與輸出。
由於改變的是全局,因此須要謹慎實用,用很差會影響到性能。
實例: 使用extra: 1:Book.objects.filter(publisher__name='廣東人員出版社').extra(where=['price>50']) Book.objects.filter(publisher__name='廣東人員出版社',price__gt=50) 2:Book.objects.extra(select={'count':'select count(*) from hello_Book'}) 使用raw: Book.objects.raw('select * from hello_Book') 自定義sql: Book.objects.raw("insert into hello_author(name) values('測試')") rawQuerySet爲惰性查詢,只有在使用時生會真正執行 執行自定義sql: from django.db import connection cursor=connection.cursor() #插入操做 cursor.execute("insert into hello_author(name) values('郭敬明')") #更新操做 cursor.execute('update hello_author set name='abc' where name='bcd'') #刪除操做 cursor.execute('delete from hello_author where name='abc'') #查詢操做 cursor.execute('select * from hello_author') raw=cursor.fetchone() #返回結果行遊標直讀向前,讀取一條 cursor.fetchall() #讀取全部
首先,定義一個實例使用的django數據庫模型Product,只是象徵性地定義了兩個字段name和price
批量建立數據使用for循環,建立數據的時候儘可能最後執行建立語句,使用django的語法 bulk_create product_list_to_insert = list() for x in range(10): product_list_to_insert.append(Product(name='product name ' + str(x), price=x)) Product.objects.bulk_create(product_list_to_insert)
---
Django ORM 中的批量操做 在Hibenate中,經過批量提交SQL操做,部分地實現了數據庫的批量操做。但在Django的ORM中的批量操做卻要完美得多,真是一個驚喜。 數據模型定義 首先,定義一個實例使用的django數據庫模型Product,只是象徵性地定義了兩個字段name和price。 from django.db import models class Product(models.Model): name = models.CharField(max_length=200) price = models.DecimalField(max_digits=10, decimal_places=2) 批量插入數據 批量插入數據時,只需先生成個一要傳入的Product數據的列表,而後調用bulk_create方法一次性將列表中的數據插入數據庫。 product_list_to_insert = list() for x in range(10): product_list_to_insert.append(Product(name='product name ' + str(x), price=x)) Product.objects.bulk_create(product_list_to_insert) 批量更新數據 批量更新數據時,先進行數據過濾,而後再調用update方法進行一次性地更新。下面的語句將生成相似update...where...的SQL語句。 Product.objects.filter(name__contains='name').update(name='new name') 批量刪除數據 批量更新數據時,先是進行數據過濾,而後再調用delete方法進行一次性地刪除。下面的語句將生成相似delete from...where...的SQL語句。 Product.objects.filter(name__contains='name query').delete() 若是是經過運行普通Python腳本的方式而不是在view中調用上述的代碼的,別忘了先在腳本中進行django的初始化: import os os.environ.setdefault("DJANGO_SETTINGS_MODULE", "testproject.settings") import django django.setup() Hibernate的所謂「批量操做」中,對每個實體的更新操做,都會生成一條update語句,而後只是把好幾個update語句一次性提交給數據庫服務器而已。對實體的刪除操做也是同樣。 Django ORM中的批量操做的實現更接近於SQL操做的體驗,運行效率也會比Hibernate中的實現更加高效。
域名解析成IP地址;
與目的主機進行TCP鏈接(三次握手);
發送與收取數據(瀏覽器與目的主機開始HTTP訪問過程);
與目的主機斷開TCP鏈接(四次揮手);
migrate 英 /maɪ'greɪt; 'maɪgreɪt/ 美 /'maɪɡret/ 移動
在pycharm的Terminal執行
數據遷移的指令
python manage.py makemigrations
python manage.py migrate
----------------------------------
1.request.method == 'GET' 2.request.method == 'POST'
1六、經常使用視圖響應的方式是什麼?
1.Httpreponse 2.render 3.redirect
1七、HTTP響應的常見狀態碼分類?
狀態碼如200 OK,以3位數字和緣由 成。數字中的 一位指定了響應 別,後兩位無分 。響應 別有以5種。
常見的HTTP狀態碼: 200 - 請求成功 301 - 資源(網頁等)被永久轉移到其它URL 404 - 請求的資源(網頁等)不存在 500 - 內部服務器錯誤
路由選擇的最長匹配原則----當路由器收到一個IP數據包時,會將數據包的目的IP地址與本身本地路由表中的表項進行bit by bit的逐位查找,直到找到匹配度最長的條目,這叫最長匹配原則
要使用緩存系統須要先在settings.py中設置,Django提供多種緩存類型:Memcached緩存,數據庫緩存,文件系統緩存,局部內存緩存和自定義緩存等
1、jsonp跨域 JSONP(JSON with Padding:填充式JSON),應用JSON的一種新方法, JSON、JSONP的區別: 1、JSON返回的是一串數據、JSONP返回的是腳本代碼(包含一個函數調用) 2、JSONP 只支持get請求、不支持post請求
2、nginx反向代理:
三、WebSocket協議跨域
域名簡稱網域
是由一串用點分隔的名字組成的Internet上某一臺計算機或計算機組的名稱,用於在數據傳輸時標識計算機的電子方位(有時也指地理位置)。
跨域:
好比從www.baidu.com 頁面去請求 www.google.com 的資源。
跨域的嚴格一點的定義是:只要 協議,域名,端口有任何一個的不一樣,就被看成是跨域
----------------------------------------------------------------------------------
跨域,指的是瀏覽器不能執行其餘網站的腳本。它是由瀏覽器的同源策略形成的,是瀏覽器施加的安全限制。
所謂同源是指,域名,協議,端口均相同
什麼是跨域? 跨域,指的是瀏覽器不能執行其餘網站的腳本。它是由瀏覽器的同源策略形成的,是瀏覽器施加的安全限制。 所謂同源是指,域名,協議,端口均相同,不明白不要緊,舉個栗子: http://www.123.com/index.html 調用 http://www.123.com/server.php (非跨域) http://www.123.com/index.html 調用 http://www.456.com/server.php (主域名不一樣:123/456,跨域) http://abc.123.com/index.html 調用 http://def.123.com/server.php (子域名不一樣:abc/def,跨域) http://www.123.com:8080/index.html 調用 http://www.123.com:8081/server.php (端口不一樣:8080/8081,跨域) http://www.123.com/index.html 調用 https://www.123.com/server.php (協議不一樣:http/https,跨域) 請注意:localhost和127.0.0.1雖然都指向本機,但也屬於跨域。 瀏覽器執行javascript腳本時,會檢查這個腳本屬於哪一個頁面,若是不是同源頁面,就不會被執行。 解決辦法: 1、JSONP: 使用方式就不贅述了,可是要注意JSONP只支持GET請求,不支持POST請求。 2、代理: 例如www.123.com/index.html須要調用www.456.com/server.php,能夠寫一個接口www.123.com/server.php,由這個接口在後端去調用www.456.com/server.php並拿到返回值,而後再返回給index.html,這就是一個代理的模式。至關於繞過了瀏覽器端,天然就不存在跨域問題。 3、PHP端修改header(XHR2方式) 在php接口腳本中加入如下兩句便可: header('Access-Control-Allow-Origin:*');//容許全部來源訪問 header('Access-Control-Allow-Method:POST,GET');//容許訪問的方式 --------------------- 做者:L瑜 來源:CSDN 原文:https://blog.csdn.net/lambert310/article/details/51683775 版權聲明:本文爲博主原創文章,轉載請附上博文連接!
Django中內置的signal 英 /'sɪgn(ə)l/ 美 /'sɪgnl/
Django中提供了"信號調度",用於在框架執行操做時解耦.
一些動做發生的時候,系統會根據信號定義的函數執行相應的操做
https://www.cnblogs.com/renpingsheng/p/7566647.html
三種繼承方式: 1、抽象基類(Abstract base classes) 二、多表繼承(Multi-table inheritance) 三、代理
在進行相對複雜的查詢時,使用 django.db.models.Q 對象。
例如須要進行復合條件的查詢的SQL語句以下:
與或非操做
is_valid()
方法,用於檢查表單提交是否正確。
級聯就是咱們說的連表的操做,連表將會使表之間經過各類關係鏈接起來,可是orm刪除的時候是指定字段的,因此須要在model的表中經過外鍵鏈接設置級聯關係刪除 user = models.FroeignKey(User, blank=True, null=True, on_delete=models.SET_NULL) 須要注意的是on_delete=models.SET_NULL的前提必須是null=true
models.SET_NULL這裏還有其餘幾個選項: * SET_NULL 當外鍵的字段被刪除的時候設置爲null前提是指定了 null=True * CASCADE 默認的選項,當外鍵關聯的字段刪除的時候,全部其餘表級聯刪除 * SET_DEFAULT 設置一個默認值,當關聯的記錄刪除的時候恢復成默認值 *DO_NOTHING django不作任何事情,數據庫返回什麼就報什麼 * SET()¶ 還能夠set一個函數,當關聯記錄刪除的時候觸發獲得一個值
cookies和session都屬於一種會話跟蹤技術
Session是服務器端技術,利用這個技術,服務器在運行時能夠 爲每個用戶的瀏覽器建立一個其獨享的session對象,因爲 session爲用戶瀏覽器獨享,
因此用戶在訪問服務器的web資源時 ,能夠把各自的數據放在各自的session中,當用戶再去訪問該服務器中的其它web資源時,其它web資源再從用戶各自的session中 取出數據爲用戶服務。
其實Cookie是key-value結構,相似於一個python中的字典
cookie的概念
Cookie翻譯成中文是小甜點,小餅乾的意思。在HTTP中它表示服務器送給客戶端瀏覽器的小甜點。其實Cookie是key-value結構,相似於一個python中的字典。
隨着服務器端的響應發送給客戶端瀏覽器。而後客戶端瀏覽器會把Cookie保存起來,當下一次再訪問服務器時把Cookie再發送給服務器。 Cookie是由服務器建立
,而後經過響應發送給客戶端的一個鍵值對。客戶端會保存Cookie,並會標註出Cookie的來源(哪一個服務器的Cookie)。當客戶端向服務器發出請求時會把全部
這個服務器Cookie包含在請求中發送給服務器,這樣服務器就能夠識別客戶端了!
當咱們在django中用到session時,cookie由服務器端隨機生成,寫到瀏覽器的cookie中,每一個瀏覽器都有本身cookie值,是session尋找用戶信息的惟一標識
session的好處:客戶端只有cookies的值,但始終沒有用戶的信息。
用法:request.session.get('k1')
request.session['k1']='v1'
session依賴於cookies,cookie保存在瀏覽器,session保存在服務器端
會從新登陸(若是A服務器的session數據不和B服務器的數據共享的話)
跨域請求能夠用jsonp來解決只能用於get,也能夠用這個插件:django-cors-headers
1.安裝django-cors-headers
2.配置settings.py文件
查詢集,也稱查詢結果集、QuerySet,表示從數據庫中獲取的對象集合。
兩大特徵是:惰性執行和 緩存
django建立 查詢 集不會訪問數據庫,直到調用數據時才訪問數據庫
當調用以下過濾器方法時,Django會返回查詢集(而不是簡單的列表): all():返回全部數據。 filter():返回知足條件的數據。 exclude():返回知足條件以外的數據。 order_by():對結果進行排序。 一:惰性執行 books = BookInfo.objects.all() # 此時,數據庫並不會進行實際查詢 # 只有當真正使用時,如遍歷的時候,纔會真正去數據庫進行查詢 for b in books: print(b) 二:緩存 使用同一個查詢集,第一次使用時會發生數據庫的查詢,而後Django會把結果緩存下來,再次使用這個查詢集時會使用緩存的數據,減小了數據庫的查詢次數 新建一個查詢集對象就能夠實現
all():返回全部數據。
filter():返回知足條件的數據。
exclude():返回知足條件以外的數據。
order_by():對結果進行排序。
urlpatterns = [ path('admin/', admin.site.urls),]
--
from django.conf.urls import url,include from arya.service.sites import site from django.urls.resolvers import RegexURLPattern from django.urls.resolvers import RegexURLResolver from django.shortcuts import HttpResponse def index(request): print(get_all_url(urlpatterns,prev='/')) return HttpResponse('...') def get_all_url(urlparrentens,prev,is_first=False,result=[]): if is_first: result.clear() for item in urlparrentens: v = item._regex.strip('^') #去掉url中的^和') #去掉url中的^和 if isinstance(item,RegexURLPattern): result.append(prev + v) else: get_all_url(item.urlconf_name,prev + v) return result urlpatterns = [ url(r'^arya/', site.urls), url(r'^index/', index), ]
路由分發
url用解耦的做用
include是路由轉發功能,由於不一樣的app針對的是不一樣的分發路由路徑,因此經過from django.conf.urls import include,來肯定導入的路由的路徑
django2.0中寫路由的正則方式須要導入re_path的方式來匹配正則表達式,直接使用會報錯,django1.xx中則沒有限制
name是給url中取一個別名
namespace名稱空間,防止多個應用之間的路由重複
namespace
url: re_path(r'^app01/', include("app01.urls",namespace="app01")), app01.urls: urlpatterns = [ re_path(r'^index/', index,name="index"), ] app01.views: from django.core.urlresolvers import reverse def index(request): return HttpResponse(reverse("app01:index"))
使用HttpResponseRedirect redirect和reverse 狀態碼:302,301
在models裏面作primary_key的設置
null 是針對數據庫而言,若是 null=True, 表示數據庫的該字段能夠爲空。
blank 是針對表單的,若是 blank=True,表示你的表單填寫該字段的時候能夠不填,好比 admin 界面下增長 model 一條記錄的時候。直觀的看到就是該字段不是粗體
django中提供choice類型
gender_choice=(('1','男'),('2','女 '))
user_gender=Models.CharFied(max_length=2,choices=gender_choice)
在查詢對象集合的時候,把指定的外鍵對象也一併完整查詢加載,避免後續的重複查詢。 1,select_related適用於外鍵和多對一的關係查詢; 2,prefetch_related適用於一對多或者多對多的查詢。
django中須要設置on_delete來設置級聯關係表
# 當前生成的書籍對象 book_obj=Book.objects.create(title="追風箏的人",price=200,publishDate="2012-11-12",publish_id=1) # 爲書籍綁定的作做者對象 yuan=Author.objects.filter(name="yuan").first() # 在Author表中主鍵爲2的紀錄 egon=Author.objects.filter(name="alex").first() # 在Author表中主鍵爲1的紀錄 # 綁定多對多關係,即向關係表book_authors中添加紀錄 book_obj.authors.add(yuan,egon) # 將某些特定的 model 對象添加到被關聯對象集合中。 ======= book_obj.authors.add(*[]) +------------------------------------------------------------------------------------------------------------------------+ book_obj.authors.remove() # 將某個特定的對象從被關聯對象集合中去除。 ====== book_obj.authors.remove(*[]) book_obj.authors.clear() #清空被關聯對象集合 book_obj.authors.set() #先清空再設置
tags = models.ManyToManyField( to="Tag", through='Article2Tag', through_fields=('article', 'tag'), )
* HTTPresponse, * jsonresponse, * redirect
from django.contrib.auth.decorators import login_required
@login_required---用於驗證是否有登陸狀態,若是沒有登陸,設置跳轉的頁面就會跳轉至未登陸狀態的頁面 @permission_required---檢查用戶是否具備特定權限是一項相對常見的任務 @get_permission_required---返回mixin使用的可迭代權限名稱。默認爲permission_required屬性,必要時轉換爲元組。 @has_permission---返回一個布爾值,表示當前用戶是否有權執行裝飾視圖
CACHES = { 'default': { 'BACKEND': 'django.core.cache.backends.locmem.LocMemCache', 'LOCATION': 'unique-snowflake' } }
本質上其實就是一個socket服務端,用戶的瀏覽器其實就是一個socket客戶端
@get和@post使用 1:在views模板下編寫測試函數(記得在urls.py文件中進行相應配置) 2:將剛剛封裝的函數所在模板引入views.py 3:使用@get進行攔截 @params,response_success,response_failure使用 第一種 @login_required def simple_view(request): return HttpResponse()123 2 經過對基於函數視圖或者基於類視圖使用一個裝飾器實現控制: @login_required(MyView.as_view())1 3 經過覆蓋mixin的類視圖的dispatch方法實現控制:
自定義過濾器@register.filter
自定義filter:{{ 參數1|filter函數名:參數2 }} # 1.能夠與if標籤來連用 # 2.自定義時須要寫兩個形參 # simple_tag:{% simple_tag函數名 參數1 參數2 %} # 1.能夠傳多個參數,沒有限制 # 2.不能與if標籤來連用 @register.simple_tag def multi_tag(x,y): return x*y
會話跟蹤技術,保留用戶 Cookie是由服務器建立,而後經過響應發送給客戶端?的一個鍵值對。 具體一個瀏覽器針對一個服務器存儲的key-value({ }) response.set_cookie("is_login",True) request.COOKIES.get("is_login")
https://mp.weixin.qq.com/s?src=11×tamp=1543650968&ver=1277&signature=14H5aRhphiu5QRsUP15kV*RpCgGIp5-BWGot2wg4rZPhMjxQNjluUCvzRO9tXb4KqgSysEFhPX2TBDKaMbyfZuzjG2P-M1BgrozF-Jj-aU33g4mMK51XAj3Xd9KKsDJl&new=1
CSRF跨站點請求僞造(Cross—Site Request Forgery)
XSS利用站點內的信任用戶,而CSRF則經過假裝來自受信任用戶的請求來利用受信任的網站。
與XSS攻擊相比,CSRF攻擊每每不大流行(所以對其進行防範的資源也至關稀少)和難以防範,因此被認爲比XSS更具危險性。
防護CSRF攻擊:
驗證HTTP_REFERER字段
請求中添加token驗證
在Http頭中自定義屬性並驗證
---
CSRF攻擊攻擊原理及過程以下: 1. 用戶C打開瀏覽器,訪問受信任網站A,輸入用戶名和密碼請求登陸網站A; 2.在用戶信息經過驗證後,網站A產生Cookie信息並返回給瀏覽器,此時用戶登陸網站A成功,能夠正常發送請求到網站A; 3. 用戶未退出網站A以前,在同一瀏覽器中,打開一個TAB頁訪問網站B; 4. 網站B接收到用戶請求後,返回一些攻擊性代碼,併發出一個請求要求訪問第三方站點A; 5. 瀏覽器在接收到這些攻擊性代碼後,根據網站B的請求,在用戶不知情的狀況下攜帶Cookie信息,向網站A發出請求。網站A並不知道該請求實際上是由B發起的,因此會根據用戶C的Cookie信息以C的權限處理該請求,致使來自網站B的惡意代碼被執行。
如今業界對CSRF的防護,一致的作法是使用一個Token(Anti CSRF Token)。 例子: 用戶訪問某個表單頁面。 服務端生成一個Token,放在用戶的Session中,或者瀏覽器的Cookie中。 在頁面表單附帶上Token參數。 用戶提交請求後, 服務端驗證表單中的Token是否與用戶Session(或Cookies)中的Token一致,一致爲合法請求,不是則非法請求。 這個Token的值必須是隨機的,不可預測的。因爲Token的存在,攻擊者沒法再構造一個帶有合法Token的請求實施CSRF攻擊。另外使用Token時應注意Token的保密性,儘可能把敏感操做由GET改成POST,以form或AJAX形式提交,避免Token泄露。 --------------------- 做者:徐彬 來源:CSDN 原文:https://blog.csdn.net/qq_33182756/article/details/80461649 版權聲明:本文爲博主原創文章,轉載請附上博文連接!
django中token防護的總體思路 第一步:django第一次響應來自某個客戶端的請求時,後端隨機產生一個token值,把這個token放到cookie中交給前端頁面; 第二步:下次前端須要發起請求的時候會攜帶者這個token,一塊兒傳給後端;Cookies:{csrftoken:xxxxx} 第三步:1.若是是經過表單發送post請求,後端會驗證cookie中的csrftoken值和表單中的csrfmiddlewaretoken是否一致 2.若是是ajax發送的post請求,後端會驗證cookie中的csrftoken值和請求頭中的X-CSRFtoken中的值是否一致 實現csrf保護 1.form提交時加上 { % csrf_token %} 2.在ajax中提交時:取到csrf的 var csrfToken = $("[name='csrfmiddlewaretoken']").val(); 加到傳輸的數據中 data: { csrfmiddlewaretoken: $("[name='csrfmiddlewaretoken']").val(), },
當用戶發起請求的時候會依次通過全部的的中間件,這個時候的請求時process_request,最後到達views的函數中,views函數處理後,在依次穿過中間件,這個時候是process_response,最後返回給請求者。
中間件中一共有四個方法:
process_request
process_view
process_exception
process_response
(1)GET提交的數據會放在URL以後,以?分割URL和傳輸數據,參數之間以&相連,如EditPost.aspx?name=test1&id=123456.POST方法是把提交的數據放在HTTP包的Body中。 (2)GET提交的數據大小有限制(由於瀏覽器對URL的長度有限制),而POST方法提交的數據沒有限制。 (3)GET方式須要使用Request.QueryString來取得變量的值,而POST方式經過Request.Form來獲取變量的值。 (4)GET方式提交數據,會帶來安全問題,好比一個登陸頁面,經過GET方式提交數據時,用戶名和密碼將出如今URL上,若是頁面能夠被緩存或者其餘人能夠訪問這臺機器,就能夠從歷史記錄得到該用戶的帳號和密碼。
一本書對應多個做者,一個做者對應多本書------>書籍和做者多對多的關係
一個出版社對應多本書------->出版社和書籍--一對多的關係
from django.db import models # Create your models here. class Author(models.Model): nid=models.AutoField(primary_key=True) name=models.CharField(max_length=32) age=models.IntegerField() class Publish(models.Model): nid=models.AutoField(primary_key=True) name=models.CharField(max_length=32) city=models.CharField(max_length=32) email=models.EmailField() class Book(models.Model): nid=models.AutoField(primary_key=True) title=models.CharField(max_length=32) publishDate=models.DateField() price=models.DecimalField(max_digits=5,decimal_places=2) # 與publish創建一對多的關係,在健在多的一方(Book) # to=表名 to_field=字段 publish=models.ForeignKey(to='Publish',to_field='nid',on_delete=models.CASCADE) # 與Author創建多對多的關係 能夠創建在兩個模型中的任意一個,自動建立第三張表 authors=models.ManyToManyField(to='Author')
反向解析
在模板中:
path('login/', views.login,name='log'), <form action='{% url 'log' %}' method='post'>
訪問 127.0.0.1:8080/login
若是後續把
path('login.html/', views.login,name='log'),
訪問 127.0.0.1:8080/login.html
在試圖函數中反向解析:
from django.urls import reverse from django.http import HttpResponseRedirect def redirect_to_year(request): # ... year = 2006 # ... return HttpResponseRedirect(reverse('news-year-archive', args=(year,))) # 同redirect("/path/")
模板 - 自定義標籤和過濾器--解決複用問題
在app中建立templatetags模塊---在文件夾下創建my_tag.py文件
自定義過濾器---有參數限制 兩個
{% load xxx %} # num=12 {{ num|filter_multi:2 }} 結果------#24
自定義標籤--沒有參數限制
一、標籤:
{% tag %}
{% endtag %}
循環序號能夠經過{{forloop}}顯示
模板繼承 (extend)
#WSGI: # web服務器網關接口,是一套協議。用於接收用戶請求並將請求進行初次封裝,而後將請求交給web框架 # 實現wsgi協議的模塊: # 1.wsgiref,本質上就是編寫一個socket服務端,用於接收用戶請求(django) # 2.werkzeug,本質上就是編寫一個socket服務端,用於接收用戶請求(flask) #uwsgi: # 與WSGI同樣是一種通訊協議,它是uWSGI服務器的獨佔協議,用於定義傳輸信息的類型 #uWSGI: # 是一個web服務器,實現了WSGI協議,uWSGI協議,http協議,
Django 內置的User類提供了用戶密碼的存儲、驗證、修改等功能,默認使用pbkdf2_sha256方式來存儲和管理用的密碼。 django經過setting.py文件中的PASSWORD_HASHERS來設置選擇要使用的算法,列表的第一個元素 (即settings.PASSWORD_HASHERS[0])
會用於儲存密碼, 全部其它元素都是用於驗證的哈希值,它們能夠用於檢查現有的密碼。意思是若是你打算使用不一樣的算法,你須要修改PASSWORD_HASHERS,來將你最喜歡的算法在列表中放在首位。 一個settings中的Password_hashers看起來是這樣的: PASSWORD_HASHERS = ( 'django.contrib.auth.hashers.PBKDF2PasswordHasher', 'django.contrib.auth.hashers.PBKDF2SHA1PasswordHasher', 'django.contrib.auth.hashers.BCryptSHA256PasswordHasher', 'django.contrib.auth.hashers.BCryptPasswordHasher', 'django.contrib.auth.hashers.SHA1PasswordHasher', 'django.contrib.auth.hashers.MD5PasswordHasher', 'django.contrib.auth.hashers.CryptPasswordHasher', ) 具體的密碼生成以及驗證明現 from django.contrib.auth.hashers import make_password,check_password pwd='4562154' mpwd=make_password(pwd,None,'pbkdf2_sha256') # 建立django密碼,第三個參數爲加密算法 pwd_bool=check_password(pwd,mpwd) # 返回的是一個bool類型的值,驗證密碼正確與否 Django之密碼加密 經過django自帶的類庫,來加密解密很方便,下面來簡單介紹下; 導入包: from django.contrib.auth.hashers import make_password, check_password 從名字就能夠看出來他們的做用了。 一個是生成密碼,一個是覈對密碼。 例如: make_password("123456") 獲得結果: u'pbkdf2_sha25615000MAjic3nDGFoi$qbclz+peplspCbRF6uoPZZ42aJIIkMpGt6lQ+Iq8nfQ=' 另外也能夠經過參數來生成密碼: >>> make_password("123456", None, 'pbkdf2_sha256') 校驗: 校驗就是經過check_password(原始值, 生成的密文)來校驗密碼的。 >>> check_password("123456","pbkdf2_sha25615000MAjic3nDGFoi$qbclz+peplspCbRF6uoPZZ42aJIIkMpGt6lQ+Iq8nfQ=") True
blank 設置爲True時,字段能夠爲空。設置爲False時,字段是必須填寫的。字符型字段CharField和TextField是用空字符串來存儲空值的。若是爲True,字段容許爲空,默認不容許。 null 設置爲True時,django用Null來存儲空值。日期型、時間型和數字型字段不接受空字符串。因此設置IntegerField,DateTimeField型字段能夠爲空時,須要將blank,null均設爲True。 若是爲True,空值將會被存儲爲NULL,默認爲False。 若是想設置BooleanField爲空時能夠選用NullBooleanField型字段。 一句話歸納 null 是針對數據庫而言,若是 null=True, 表示數據庫的該字段能夠爲空。NULL represents non-existent data. blank 是針對表單的,若是 blank=True,表示你的表單填寫該字段的時候能夠不填。好比 admin 界面下增長 model 一條記錄的時候。直觀的看到就是該字段不是粗體
在HttpRequest對象中, GET和POST屬性是django.http.QueryDict類的實例。 QueryDict相似字典的自定義類,用來處理單鍵對應多值的狀況。 在 HttpRequest 對象中,屬性 GET 和 POST 獲得的都是 django.http.QueryDict 所建立的實例。這是一個 django 自定義的相似字典的類,用來處理同一個鍵帶多個值的狀況。 在 python 原始的字典中,當一個鍵出現多個值的時候會發生衝突,只保留最後一個值。而在 HTML 表單中,一般會發生一個鍵有多個值的狀況,例如 <select multiple> (多選框)就是一個很常見狀況。 request.POST 和request.GET 的QueryDict 在一個正常的請求/響應循環中是不可變的。若要得到可變的版本,須要使用.copy()方法。 django QuerySet對象轉換成字典對象 >manage.py shell >>> from django.contrib.auth.models import User >>> from django.forms.models import model_to_dict >>> u = User.objects.get(id=1) >>> u_dict = model_to_dict(u) >>> type(u) <class 'django.contrib.auth.models.User'> >>> type(u_dict) <type 'dict'> 1.QueryDict.__init__(query_string=None, mutable=False, encoding=None) 這是一個構造函數,其中 query_string 須要一個字符串,例如: >>> QueryDict('a=1&a=2&c=3') <QueryDict: {'a': ['1', '2'], 'c': ['3']}>