Django中的CSRF

来源:http://www.cnblogs.com/chenchao1990/archive/2016/03/31/5339779.html
-Advertisement-
Play Games

CSRF(Cross Site Request Forgery, 跨站域請求偽造) CSRF 背景與介紹 CSRF(Cross Site Request Forgery, 跨站域請求偽造)是一種網路的攻擊方式,它在 2007 年曾被列為互聯網 20 大安全隱患之一。其他安全隱患,比如 SQL 腳本註 ...


CSRF(Cross Site Request Forgery, 跨站域請求偽造)

 

CSRF 背景與介紹

CSRF(Cross Site Request Forgery, 跨站域請求偽造)是一種網路的攻擊方式,它在 2007 年曾被列為互聯網 20 大安全隱患之一。其他安全隱患,比如 SQL 腳本註入,跨站域腳本攻擊等在近年來已經逐漸為眾人熟知,很多網站也都針對他們進行了防禦。然而,對於大多數人來說,CSRF 卻依然是一個陌生的概念。即便是大名鼎鼎的 Gmail, 在 2007 年底也存在著 CSRF 漏洞,從而被黑客攻擊而使 Gmail 的用戶造成巨大的損失。

 

CSRF 攻擊實例

 

 

CSRF 攻擊可以在受害者毫不知情的情況下以受害者名義偽造請求發送給受攻擊站點,從而在並未授權的情況下執行在許可權保護之下的操作。比如說,受害者 Bob 在銀行有一筆存款,通過對銀行的網站發送請求 http://bank.example/withdraw?account=bob&amount=1000000&for=bob2 可以使 Bob 把 1000000 的存款轉到 bob2 的賬號下。通常情況下,該請求發送到網站後,伺服器會先驗證該請求是否來自一個合法的 session,並且該 session 的用戶 Bob 已經成功登陸。黑客 Mallory 自己在該銀行也有賬戶,他知道上文中的 URL 可以把錢進行轉帳操作。Mallory 可以自己發送一個請求給銀行:http://bank.example/withdraw?account=bob&amount=1000000&for=Mallory。但是這個請求來自 Mallory 而非 Bob,他不能通過安全認證,因此該請求不會起作用。這時,Mallory 想到使用 CSRF 的攻擊方式,他先自己做一個網站,在網站中放入如下代碼: src=”http://bank.example/withdraw?account=bob&amount=1000000&for=Mallory ”,並且通過廣告等誘使 Bob 來訪問他的網站。當 Bob 訪問該網站時,上述 url 就會從 Bob 的瀏覽器發向銀行,而這個請求會附帶 Bob 瀏覽器中的 cookie 一起發向銀行伺服器。大多數情況下,該請求會失敗,因為他要求 Bob 的認證信息。但是,如果 Bob 當時恰巧剛訪問他的銀行後不久,他的瀏覽器與銀行網站之間的 session 尚未過期,瀏覽器的 cookie 之中含有 Bob 的認證信息。這時,悲劇發生了,這個 url 請求就會得到響應,錢將從 Bob 的賬號轉移到 Mallory 的賬號,而 Bob 當時毫不知情。等以後 Bob 發現賬戶錢少了,即使他去銀行查詢日誌,他也只能發現確實有一個來自於他本人的合法請求轉移了資金,沒有任何被攻擊的痕跡。而 Mallory 則可以拿到錢後逍遙法外。

 

CSRF 攻擊的對象

在討論如何抵禦 CSRF 之前,先要明確 CSRF 攻擊的對象,也就是要保護的對象。從以上的例子可知,CSRF 攻擊是黑客藉助受害者的 cookie 騙取伺服器的信任,但是黑客並不能拿到 cookie,也看不到 cookie 的內容。另外,對於伺服器返回的結果,由於瀏覽器同源策略的限制,黑客也無法進行解析。因此,黑客無法從返回的結果中得到任何東西,他所能做的就是給伺服器發送請求,以執行請求中所描述的命令,在伺服器端直接改變數據的值,而非竊取伺服器中的數據。所以,我們要保護的對象是那些可以直接產生數據改變的服務,而對於讀取數據的服務,則不需要進行 CSRF 的保護。比如銀行系統中轉賬的請求會直接改變賬戶的金額,會遭到 CSRF 攻擊,需要保護。而查詢餘額是對金額的讀取操作,不會改變數據,CSRF 攻擊無法解析伺服器返回的結果,無需保護。

 

 

防禦策略:在請求地址中添加 token 並驗證

CSRF 攻擊之所以能夠成功,是因為黑客可以完全偽造用戶的請求,該請求中所有的用戶驗證信息都是存在於 cookie 中,因此黑客可以在不知道這些驗證信息的情況下直接利用用戶自己的 cookie 來通過安全驗證。要抵禦 CSRF,關鍵在於在請求中放入黑客所不能偽造的信息,並且該信息不存在於 cookie 之中。可以在 HTTP 請求中以參數的形式加入一個隨機產生的 token,併在伺服器端建立一個攔截器來驗證這個 token,如果請求中沒有 token 或者 token 內容不正確,則認為可能是 CSRF 攻擊而拒絕該請求。

token 可以在用戶登陸後產生並放於 session 之中,然後在每次請求時把 token 從 session 中拿出,與請求中的 token 進行比對,但這種方法的難點在於如何把 token 以參數的形式加入請求。對於 GET 請求,token 將附在請求地址之後,這樣 URL 就變成 http://url?csrftoken=tokenvalue。 而對於 POST 請求來說,要在 form 的最後加上 <input type=”hidden” name=”csrftoken” value=”tokenvalue”/>,這樣就把 token 以參數的形式加入請求了。但是,在一個網站中,可以接受請求的地方非常多,要對於每一個請求都加上 token 是很麻煩的,並且很容易漏掉,通常使用的方法就是在每次頁面載入時,使用 javascript 遍歷整個 dom 樹,對於 dom 中所有的 a 和 form 標簽後加入 token。這樣可以解決大部分的請求,但是對於在頁面載入之後動態生成的 html 代碼,這種方法就沒有作用,還需要程式員在編碼時手動添加 token。

 

 

Django 中使用CSRF

How to use it

To take advantage of CSRF protection in your views, follow these steps:

  1. The CSRF middleware is activated by default in the MIDDLEWARE_CLASSES setting. If you override that setting, remember that 'django.middleware.csrf.CsrfViewMiddleware' should come before any view middleware that assume that CSRF attacks have been dealt with.

    If you disabled it, which is not recommended, you can use csrf_protect() on particular views you want to protect (see below).

  2. In any template that uses a POST form, use the csrf_token tag inside the <form> element if the form is for an internal URL, e.g.:

    <form action="" method="post">{% csrf_token %}
    

    This should not be done for POST forms that target external URLs, since that would cause the CSRF token to be leaked, leading to a vulnerability.

  3. In the corresponding view functions, ensure that RequestContext is used to render the response so that {%csrf_token %} will work properly. If you’re using the render() function, generic views, or contrib apps, you are covered already since these all use RequestContext.

 

這段意思就是

1、不推薦禁用掉django中的CSRF。

2、我們可以再html頁面的form表單中添加csrf_token,帶著表單的請求一起發送到伺服器去驗證。

<form  enctype="multipart/form-data" method="post" action="{% url 'new_article' %}">
    {% csrf_token %}

3、在後端一定要使用render()的方法返回數據。

return render(request, 'article_new.html', {'article_list': article_list})

  

 

CSRF with AJAX

 

While the above method can be used for AJAX POST requests, it has some inconveniences: you have to remember to pass the CSRF token in as POST data with every POST request. For this reason, there is an alternative method: on each XMLHttpRequest, set a custom X-CSRFToken header to the value of the CSRF token. This is often easier, because many JavaScript frameworks provide hooks that allow headers to be set on every request.

As a first step, you must get the CSRF token itself. The recommended source for the token is the csrftokencookie, which will be set if you’ve enabled CSRF protection for your views as outlined above.

 

// using jQuery
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');

  

 

The above code could be simplified by using the JavaScript Cookie library to replace getCookie:

var csrftoken = Cookies.get('csrftoken');

  

  

Finally, you’ll have to actually set the header on your AJAX request, while protecting the CSRF token from being sent to other domains using settings.crossDomain in jQuery 1.5.1 and newer:

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);
        }
    }
});

  

 


您的分享是我們最大的動力!

-Advertisement-
Play Games
更多相關文章
  • 1、讀取網路中html網頁內容,獲取網頁中元素body內的html,處理所有img元素的src屬性後以字元串返回 2、通過HtmlAgilityPack Html操作類庫將html格式的字元串載入為html文檔對象,再對html dom進行操作 持續更新中,敬請期待... ...
  • SqlHelper類 作用:充當一個助人為樂的角色。這個類呢,任何類都可以調用。例如:數據的“增, 刪, 改 ,查”,資料庫的鏈接,等等。 這個類是靜態類,只要用類名.方法名(),就可以使用該方法的功能了。 作用:簡化代碼,提高性能,提高運行效率。 string sql = "select * fr ...
  • 不做開篇廢話,我們發現: AdaptiveTrigger 不夠好 我們知道,UWP可以在一個頁面適應不同尺寸比例的屏幕。一般來說這個功能是通過官方推薦的AdaptiveTrigger 進行的。 比如這樣: 我們可以看到這樣的的Trigger制定了最小值,隱含了條件“當滿足長寬都大於於這個條件時,這個 ...
  • 上面兩章,主要講基本的配置,今天我們來做一個比較有趣的東西,為每個客戶加一個頭像圖片。如果我們圖片保存在自己的伺服器,對於伺服器要求有點高,每次下載的時候,都會阻塞網路介面,要是1000個人同時訪問這張圖片,會徹底報廢掉整個網路。如果你跟我一樣,在小公司,沒有自己專業的圖片伺服器,又想用圖片,那就跟 ...
  • 偶然在國外一個網站瞅到的,非常的酷,發出來共用一下。一般來說,Python和Java,C#一樣是沒有尾遞歸自動優化的能力的,遞歸調用受到調用棧長度的限制被廣泛的詬病,但是這個狂人用一個匪夷所思的方法解決了這個問題併在Python上實現了,從此Python的遞歸調用再也不用受到調用棧長度的制約,太酷了 ...
  • 說明:找到最大的數,排列到最後面,然後繼續找 例: $arr = array(3,5,-1,0,2); for($i=0;$i<count($arr)-1;$i++){ for($j=0;$j<count($arr)-1-$i;$j++){ if($arr[$j]>$arr[$j+1]){ $tem ...
  • 漢字字元的編碼為雙位元組,對於漢字字元和單位元組字元混排的情況,如果目標截取的字元串內只包含奇數個單位元組字元,則會出現半個漢字字元的問題。如下所示: (1)天水市秦州區南郭路2號(工行七里墩分理處? --包含數字字元,單位元組。 (2)七里河區金港城金福花園20號樓3號(金港城?--包含數字字元,單位元組。 ...
  • 一元運算符: 二元運算符 三元運算符 ...
一周排行
    -Advertisement-
    Play Games
  • 移動開發(一):使用.NET MAUI開發第一個安卓APP 對於工作多年的C#程式員來說,近來想嘗試開發一款安卓APP,考慮了很久最終選擇使用.NET MAUI這個微軟官方的框架來嘗試體驗開發安卓APP,畢竟是使用Visual Studio開發工具,使用起來也比較的順手,結合微軟官方的教程進行了安卓 ...
  • 前言 QuestPDF 是一個開源 .NET 庫,用於生成 PDF 文檔。使用了C# Fluent API方式可簡化開發、減少錯誤並提高工作效率。利用它可以輕鬆生成 PDF 報告、發票、導出文件等。 項目介紹 QuestPDF 是一個革命性的開源 .NET 庫,它徹底改變了我們生成 PDF 文檔的方 ...
  • 項目地址 項目後端地址: https://github.com/ZyPLJ/ZYTteeHole 項目前端頁面地址: ZyPLJ/TreeHoleVue (github.com) https://github.com/ZyPLJ/TreeHoleVue 目前項目測試訪問地址: http://tree ...
  • 話不多說,直接開乾 一.下載 1.官方鏈接下載: https://www.microsoft.com/zh-cn/sql-server/sql-server-downloads 2.在下載目錄中找到下麵這個小的安裝包 SQL2022-SSEI-Dev.exe,運行開始下載SQL server; 二. ...
  • 前言 隨著物聯網(IoT)技術的迅猛發展,MQTT(消息隊列遙測傳輸)協議憑藉其輕量級和高效性,已成為眾多物聯網應用的首選通信標準。 MQTTnet 作為一個高性能的 .NET 開源庫,為 .NET 平臺上的 MQTT 客戶端與伺服器開發提供了強大的支持。 本文將全面介紹 MQTTnet 的核心功能 ...
  • Serilog支持多種接收器用於日誌存儲,增強器用於添加屬性,LogContext管理動態屬性,支持多種輸出格式包括純文本、JSON及ExpressionTemplate。還提供了自定義格式化選項,適用於不同需求。 ...
  • 目錄簡介獲取 HTML 文檔解析 HTML 文檔測試參考文章 簡介 動態內容網站使用 JavaScript 腳本動態檢索和渲染數據,爬取信息時需要模擬瀏覽器行為,否則獲取到的源碼基本是空的。 本文使用的爬取步驟如下: 使用 Selenium 獲取渲染後的 HTML 文檔 使用 HtmlAgility ...
  • 1.前言 什麼是熱更新 游戲或者軟體更新時,無需重新下載客戶端進行安裝,而是在應用程式啟動的情況下,在內部進行資源或者代碼更新 Unity目前常用熱更新解決方案 HybridCLR,Xlua,ILRuntime等 Unity目前常用資源管理解決方案 AssetBundles,Addressable, ...
  • 本文章主要是在C# ASP.NET Core Web API框架實現向手機發送驗證碼簡訊功能。這裡我選擇是一個互億無線簡訊驗證碼平臺,其實像阿裡雲,騰訊雲上面也可以。 首先我們先去 互億無線 https://www.ihuyi.com/api/sms.html 去註冊一個賬號 註冊完成賬號後,它會送 ...
  • 通過以下方式可以高效,並保證數據同步的可靠性 1.API設計 使用RESTful設計,確保API端點明確,並使用適當的HTTP方法(如POST用於創建,PUT用於更新)。 設計清晰的請求和響應模型,以確保客戶端能夠理解預期格式。 2.數據驗證 在伺服器端進行嚴格的數據驗證,確保接收到的數據符合預期格 ...