Django之CSRF

1、什麼是CSRFjavascript

    CSRF, Cross Site Request Forgery, 跨站僞造請求。舉例來說,某個惡意的網站上有一個指向你的網站的連接,若是某個用戶已經登陸到你的網站上了,那麼當這個用戶點擊這個惡意網站上的那個連接時,就會向你的網站發來一個請求,你的網站會覺得這個請求是用戶本身發來的,其實呢,這個請求是那個惡意網站僞造的。前端

    Django爲用戶實現跨站請求僞造保護的功能,經過中間件 django.middleware.csrf.CsrfViewMiddleware 來完成。而對於django中設置防跨站請求僞造功能有分爲全局設置和局部設置。java


2、Django提供CSRF防禦機制python

    Django第一次響應某個客戶端的請求時,會在服務器端隨機生成一個token,而後把這個token放到cookie中返回給客戶端。而後客戶端每次POST請求時都會帶上這個token,這樣就避免了CSRF***。
jquery

  • 在返回的HTTP響應的cookie中,Django會添加一個csrftoken字段,值爲隨機生成的tokenajax

  • 在POST表單中,必須包含一個csrfmiddlewaretoken隱藏字段,須要在模板中添加{% csrf_token %}自動生成django

  • 在處理POST請求以前,Django會驗證cookie中csrftoken和表單中csrfmiddlewaretoken的值是否一致。若是一致,則代表這是一個合法請求。不然這個請求就是僞造的,返回403 Forbidden。服務器

  • 在Ajax POST請求中,添加一個"X-CSRFToken"頭部,值爲cookie中的csrftoken的值。cookie


3、CSRF設置ide

1. 全局設置(中間件)

django.middleware.csrf.CsrfViewMiddleware

2. 局部設置(視圖函數)

from django.views.decorators.csrf import csrf_exempt,csrf_protect

@csrf_protect  # 爲當前函數強制設置防跨站請求僞造功能,即使settings中沒有設置CSRF中間件。
def func():
    pass
    
@csrf_exempt  # 取消當前函數防跨站請求僞造功能,即使settings中設置了CSRF中間件。
def func():
    pass


4、應用CSRF

1. 前端Form表單中設置CSRF

<form method="post">
{% csrf_token %}
    ...
</form>

2. 自動在每一個Ajax請求頭部中添加"X-CSRFToken"

// 導入jquery.cookie.js 經過$.cookie('csrftoken')獲取csrf_token
// beforeSend在每一個Ajax請求以前自動設置請求頭部"X-CSRFToken"

<script src="/static/plugin/jquery/jquery-1.8.0.js"></script>
<script src="/static/plugin/jquery/jquery.cookie.js"></script>
<script type="text/javascript">
	var csrftoken = $.cookie('csrftoken');

	function csrfSafeMethod(method) {
		// these HTTP methods do not require CSRF protection
		return (/^(GET|HEAD|OPTIONS|TRACE)$/.test(method));
	}
	$.ajaxSetup({
		beforeSend: function(xhr, settings) {
			if (!csrfSafeMethod(settings.type) && !this.crossDomain) {
				xhr.setRequestHeader("X-CSRFToken", csrftoken);
			}
		}
	});
</script>

3. 單獨在Ajax請求中設置"X-CSRFToken"頭部

<script src="/static/plugin/jquery/jquery-1.8.0.js"></script>
<script src="/static/plugin/jquery/jquery.cookie.js"></script>
<script type="text/javascript">
	$.ajax({
	    headers:{"X-CSRFToken":$.cookie('csrftoken')},
	    ...
        })
</script>
相關文章
相關標籤/搜索