跨站請求偽造(csrf)中間件整理


一. CSRF中間件  

  字面意思跨站請求偽造; 即模仿個請求朝服務器發送,django中對跨站偽造的請求有相應的校驗

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

    csrf_exempt  給單個視圖排除校驗,以裝飾器形式給某個視圖加上,則該視圖就不會進行校驗

                局部禁用的前提是全局有校驗

    csrf_protect  給單個視圖必須校驗,以裝飾器形式給某個視圖加上,則該視圖就必須進行校驗

                即使注釋調settings中的46行也必須得校驗.  局部使用的前提是全局沒有校驗

二. csrt源碼解析其校驗的本質大概流程是:

  1. process_request,從請求的cookie中獲取csrftoken的值,保存為scrf_token

  2. process_view:

     > 如果視圖函數加上了csrf_exempt的裝飾器  不做校驗

     > 如果請求方式是'GET', 'HEAD', 'OPTIONS', 'TRACE' 也不做校驗

     > 其它的請求方式就要進行校驗了,校驗的實質如下:

       1.request.POST中獲取csrfmiddlewaretoken對象的值

       2.從請求頭中獲取csrfmiddlewaretoken對象的值

       3.用獲取到的csrfmiddlewaretoken的值和csrftoken的值做比較,如果校驗成功,流程繼續;校驗不成功

          則拒絕;  12中只要有1個能獲取到csrfmiddlewaretoken的值即可,不用兩個中都有.

總結: 兩點要求,1.瀏覽器必須帶有cookie;  2. post請求體中或請求頭中要能獲取到csrfmiddlewaretoken

 

三.針對以上總結的兩點,做相應的處理,處理辦法如下

     確保瀏覽器帶有cookie的兩種方式:

          > form表單內加入{% csrf_token %}

          > 不使用{% csrf_token %},導入from django.views.decorators.csrf import ensure_csrf_cookie

             ensure_csrf_cookie以裝飾器形式加在視圖上,保證返回的相應有cookie

      確保能從post請求體中或請求頭信息中獲取到csrfmiddlewaretokende的方式:

        > 頁面中加入{% csrf_token %}標簽

         1.獲取標簽值,加入post請求體中,  csrfmiddlewaretoken: $('[name="csrfmiddlewaretoken"]').val()

         2.獲取標簽值,加入post請求頭中,  headers: {"X-CSRFToken": $('[name="csrfmiddlewaretoken"]').val()}

        > 上面12都是給單個的ajax請求加csrfmiddlewaretokende,這里再介紹個通過引入js文件形式

          給全局所有ajax頭部加入csrfmiddlewaretokende的辦法,代碼思路如下: (萬能辦法)

         1.通過django官網提供的代碼來實現,首先項目下static文件夾內新建js文件,復制以下代碼:

         2.script標簽在html頁面導入新建的這個a.js文件, <script src=’/static/a.js’></script>

           它的作用是給每個請求頭信息上加crsfmiddlewaretoken信息

     猜測: 引入js文件形式可同時讓瀏覽器帶cookie和讓請求頭帶crsfmiddlewaretoken信息,因為使用

           CBVajax文件上傳時,html中沒加{%csrf_token%},views中也沒用ensure_csrf_token裝飾器

 

四. js文件代碼如下:

function getCookie(name) {

    var cookieValue = null;

    if (document.cookie && document.cookie !== '') {

        var cookies = document.cookie.split(';');

        for (var i = 0; i < cookies.length; i++) {

            var cookie = jQuery.trim(cookies[i]);

            // Does this cookie string begin with the name we want?

            if (cookie.substring(0, name.length + 1) === (name + '=')) {

                cookieValue = decodeURIComponent(cookie.substring(name.length + 1));

                break;

            }

        }

    }

    return cookieValue;

}

var csrftoken = getCookie('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);

    }

  }

});


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM