16

ドキュメントgetCookieの関数を使用して値を取得します。djangocsrfmiddlewaretoken

私は次のajax呼び出しを持っています:

var url = reverse_removeprofile.replace(/deadbeef/, key);
$.ajax({
    type:          "DELETE",
    url:           url,
    data:          "csrfmiddlewaretoken=" + getCookie("csrftoken"),
    success:       function() { ... },
});

このコードが実行されるdjangoと、CSRF検証が失敗したことを通知する403例外が発生します。しかし、私がtypeからDELETEに変更した場合、POSTそれdjangoについては満足しており、まったく文句を言いません。

これについてGoogleで役立つものを見つけることはできませんでしたが、この(現在は閉鎖され修正されている)チケットを見つけました:https ://code.djangoproject.com/ticket/15258

私がそれを正しく理解していれば、この問題は1.4マイルストーンで修正されています。DELETEdjango 1.4を使用していますが、リクエストでCSRFトークンを確認できません。

ここで何かが足りませんか?

4

2 に答える 2

40

これはjQueryのバグのようです。これは、DELETEデータをURL(GETリクエストなど)に添付するか、リクエスト本文(POSTなど)に添付するかについての混乱が原因です。

このバグレポートを参照してください。

おそらく、AJAX呼び出しに代替のCSRFメソッドを使用X-CSRFTokenし、リクエストにヘッダーを設定することで、これを回避できます。AJAX呼び出しを次のように変更してみてください。

$.ajax({
    type: "DELETE",
    url: url,
    beforeSend: function(xhr) {
        xhr.setRequestHeader("X-CSRFToken", getCookie("csrftoken"));
    },
    success: function() { ... },
});
于 2012-10-26T15:38:03.860 に答える
0

DELETEリクエストに関しては、DJangoはリクエスト本文でチェックしないことに注意してくださいcsrfmiddlewaretoken。むしろそれはX-CSRFTokenヘッダーを探します

DJango CSRFMiddlewareの動作に入ると、リクエストが次のタイプの場合、DJangoがリクエスト本文でdjango > middleware > csrf.py > CsrfViewMiddlewareスキャンしないことが非常に明確なソースコードを確認できます。csrfmiddlewaretokenDELETE

        # Check non-cookie token for match.
        request_csrf_token = ""
        if request.method == "POST":
            try:
                request_csrf_token = request.POST.get('csrfmiddlewaretoken', '')
            except OSError:
                # Handle a broken connection before we've completed reading
                # the POST data. process_view shouldn't raise any
                # exceptions, so we'll ignore and serve the user a 403
                # (assuming they're still listening, which they probably
                # aren't because of the error).
                pass

        if request_csrf_token == "":
            # Fall back to X-CSRFToken, to make things easier for AJAX,
            # and possible for PUT/DELETE.
            request_csrf_token = request.META.get(settings.CSRF_HEADER_NAME, '')
于 2021-11-29T17:29:05.163 に答える