使用 csrfmiddlewaretoken 和 csrftoken cookie 设置的 Ajax POST 仍然会出现 django 403 Forbidden

标签 ajax django-csrf csrf-protection

我读到 csrfmiddlewaretoken 和 csrftoken cookie 都必须是 django POST 请求成功的正确值( django: csrftoken COOKIE vs. csrfmiddlewaretoken HTML Form value )。我的情况就是这样,但我仍然得到 403:

在 Chrome 控制台中:

document.cookie

返回

"csrftoken=Wt9eeJop5Vb3OmeNTvogegckm1pVM5MD"

但是

$.get('https://learningdollars.fwd.wf/csrftoken/', function(data){
    console.log(data)
    token = $.parseHTML(data)[0].value
    console.log(token)
    $.ajax({
        type: "POST",
        url: 'https://learningdollars.fwd.wf/confirmemail/',
        data: {email: '<a href="https://stackoverflow.com/cdn-cgi/l/email-protection" class="__cf_email__" data-cfemail="f89f9c998b8db899948d959691d68b8c99969e978a9cd69d9c8d" rel="noreferrer noopener nofollow">[email protected]</a>', csrfmiddlewaretoken: token},
        contentType: "application/json"
    })
    .done(function(response) {
        console.log('done!')
    })
    .fail(function(error) {
        console.log('fail!')
    })
})

返回

> Object {readyState: 1, getResponseHeader: function, getAllResponseHeaders: function, setRequestHeader: function, overrideMimeType: function…}
> <input type='hidden' name='csrfmiddlewaretoken' value='Wt9eeJop5Vb3OmeNTvogegckm1pVM5MD' />
> Wt9eeJop5Vb3OmeNTvogegckm1pVM5MD
> POST https://learningdollars.fwd.wf/confirmemail/ 403 (Forbidden)
> fail! 

我有

'django.middleware.csrf.CsrfViewMiddleware',

在我的 django 中间件中激活。

我的根 urls.py 包含:

url(r'^csrftoken/$', views.get_csrf_token),
url(r'^confirmemail/$', views.confirm_email, name='confirm_email'),

而且,我的观点是:

def get_csrf_token(request):
    c = {}
    c.update(csrf(request))
    print c
    return render_to_response('csrf.html', c)

def confirm_email(request):
    print 'here'
    return JsonResponse({'response': 0})

顺便说一句,csrf.html 的内容只是 csrftoken(在输入标记内):

{% csrf_token %}

我做错了什么?

最佳答案

好吧,我找到了解决方案。它只是以 URI 而不是 json 的形式发送数据。 (顺便说一下,我尝试在上面指定 dataType: 'json' ,但没有成功。)以下是在 chrome 控制台中:

> email = '<a href="https://stackoverflow.com/cdn-cgi/l/email-protection" class="__cf_email__" data-cfemail="72151613010732131e071f1c1b5c0106131c141d00165c171607" rel="noreferrer noopener nofollow">[email protected]</a>'
< "<a href="https://stackoverflow.com/cdn-cgi/l/email-protection" class="__cf_email__" data-cfemail="d0b7b4b1a3a590b1bca5bdbeb9fea3a4b1beb6bfa2b4feb5b4a5" rel="noreferrer noopener nofollow">[email protected]</a>"

> csrftoken = 'L2MxD1XQIF1Xto5NkzUgGUYiHPyyz3K5'
< "L2MxD1XQIF1Xto5NkzUgGUYiHPyyz3K5"

> $.ajax({
    type: "POST",
    url: 'https://learningdollars.fwd.wf/confirmemail/',
    data: "email="+ encodeURI(email) + "&csrfmiddlewaretoken=" + encodeURI(csrftoken),
    success: function(data) { console.log(data); }
})

< Object {response: 1}

仍然不确定我在 json 方面做错了什么,但以下是我尝试过的:

$.ajax({
    type: "POST",
    url: "https://learningdollars.fwd.wf/confirmemail/",
    data: JSON.stringify({ email: email, csrfmiddlewaretoken: csrftoken }),
    contentType: "application/json; charset=utf-8",
    dataType: "json",
    success: function(data){
        alert(data);
    },
    failure: function(errMsg) {
        alert(errMsg);
    }
});

关于使用 csrfmiddlewaretoken 和 csrftoken cookie 设置的 Ajax POST 仍然会出现 django 403 Forbidden,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/26217637/

相关文章:

ajax - 将 JQuery 添加到使用 AJAX 加载的内容中

django - 如何从命令行获取 CSRF token ?

angularjs - Django Rest框架+AngularJS : Correct way for CSRF Protection?

php - laravel 5 csrf_token 值为空

node.js - 为什么远程服务器响应在获取请求后不包含 nodejs 上的 x-csrf-token?

javascript - 发送 XMLHttpRequest 时缓存结果有问题吗?

javascript - 通过AJAX响应更改图像的 'src'属性

django - 如何将 POST 数据中的 CSRF token 传递给 Django?

python - Django 和 Angular POST 请求 - CSRF 失败

php - JSON:从另一个域检索 JSON 文件