Django X-CSRF令牌已设置,但仍被禁止403

2022-04-08 00:00:00 python django csrf django-csrf

问题描述

我开发了一个Django文件上传API,它从客户端接收发布的数据,并将数据保存为文件。

Django CSRF manual根据Django CSRF manual,HTTP请求头部应该使用csrfToken cookie值设置X-CSRFToken。我已经通过下面的代码设置了X-CSRFToken,但Django服务器仍然禁止(403)POST请求,如下图所示。

$(document).ready(function(){
    var authid
    $.get("http://localhost:8000/v1/getAuthID?username=testuser1&password=123", function(data){
        authid = data["authid"];
        var csrftoken = $.cookie('csrftoken');
        console.log(csrftoken);

        $.ajaxSetup({
            beforeSend: function(xhr, settings) {
                xhr.setRequestHeader("X-CSRFToken", csrftoken);
            }
        });

        url = "http://localhost:8000/v1/file".replace("{authid}", authid).replace("{token}", csrftoken)
        $.post(url, function(data){
        })
    })
})

您如何通过向Django服务器发送POST请求来克服Django CSRF?

谢谢!

csrf

我使用下面的推荐答案代码来处理AJAX调用的整个CSRF主题:

// This function gets cookie with a given name
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 functions below will create a header with csrftoken
*/

function csrfSafeMethod(method) {
    // these HTTP methods do not require CSRF protection
    return (/^(GET|HEAD|OPTIONS|TRACE)$/.test(method));
}
function sameOrigin(url) {
    // test that a given url is a same-origin URL
    // url could be relative or scheme relative or absolute
    var host = document.location.host; // host + port
    var protocol = document.location.protocol;
    var sr_origin = '//' + host;
    var origin = protocol + sr_origin;
    // Allow absolute or scheme relative URLs to same origin
    return (url == origin || url.slice(0, origin.length + 1) == origin + '/') ||
        (url == sr_origin || url.slice(0, sr_origin.length + 1) == sr_origin + '/') ||
        // or any other URL that isn't scheme relative or absolute i.e relative.
        !(/^(//|http:|https:).*/.test(url));
}

$.ajaxSetup({
    beforeSend: function(xhr, settings) {
        if (!csrfSafeMethod(settings.type) && sameOrigin(settings.url)) {
            // Send the token to same-origin, relative URLs only.
            // Send the token only if the method warrants CSRF protection
            // Using the CSRFToken value acquired earlier
            xhr.setRequestHeader("X-CSRFToken", csrftoken);
        }
    }
});

只需将其包含在JQuery之后。

相关文章