簡體   English   中英

CSRF 令牌丟失或不正確

[英]CSRF Token missing or incorrect

這里是 Django 的初學者,我已經嘗試解決這個問題很長時間了。 我的中間件類中確實有“django.middleware.csrf.CsrfViewMiddleware”,並且我的帖子表單中確實有令牌。

這是我的代碼,我做錯了什么?

from django.contrib.auth.forms import UserCreationForm
from django.shortcuts import render_to_response
from django.http import HttpResponseRedirect
from chartsey.authentication.forms import RegistrationForm
from django.template import RequestContext
from django.core.context_processors import csrf

def register(request):

    if request.method == 'POST':
        c = RequestContext(request.POST, {})
        form = RegistrationForm(c)
        if form.is_valid():
            new_user = form.save()
            return HttpResponseRedirect("/")
    else:
        form = RegistrationForm()

    return render_to_response("register.html",  {'form': form,  }, )

這是我的模板:

{% block content %}

    <h1>Register</h1>
    <form action="" method="POST"> {% csrf_token %}
        {{ form.as_p }}
    <input type="submit" value="Submit">
    </form>

{% endblock %}

更新:這個答案來自 2011 年。CSRF 今天很容易。

這些天你應該使用render快捷函數return render(request, 'template.html')它自動使用RequestContext所以下面的建議已經過時了 8 年。

  1. 使用render https://docs.djangoproject.com/en/2.2/topics/http/shortcuts/
  2. 添加 CSRF 中間件https://docs.djangoproject.com/en/2.2/ref/csrf/
  3. 使用{% csrf_token %}模板標簽
  4. 確認您看到正在生成的 CSRF 令牌值,並在您的表單請求中提交

原始回復

我的猜測是您在模板中有標簽,但它沒有呈現任何內容(或者您的意思是您在實際的 HTML 中確認正在生成 CSRF 令牌?)

要么使用RequestContext而不是字典

render_to_response("foo.html", RequestContext(request, {}))

或者確保您的CONTEXT_PROCESSORS設置中有django.core.context_processors.csrf

https://docs.djangoproject.com/en/dev/ref/contrib/csrf/

或者手動將令牌添加到您的上下文中

只需將此添加到您的視圖中

return render_to_response("register.html", {'form': form, }, context_instance = RequestContext(request))

它會起作用!!

嘗試使用render而不是render_to_response

from django.shortcuts import render

render(request, "foo.html", {})

Django - render()、render_to_response() 和 direct_to_template() 之間有什么區別?

如上面的鏈接所述,它是在 Django 1.3 中引入的,並自動使用RequestContext

對於 Django 3.0 版,添加以下注釋

@csrf_protect
def yourfunc(request):
    return render(request, '../your.html', None)

並且不要忘記在您的字段中添加以下標簽

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

如果您沒有使用 CsrfViewMiddleware,那么您必須在任何使用 csrf_token 模板標記的視圖以及接受 POST 數據的視圖上使用 csrf_protect。

加入RequestContext使用時是關鍵render_to_response通過@Yuji“富田”富田和@Njogu Mbau提及。 然而,最初扔我什么,當我有這個問題掙扎的是,我不得不添加RequestContext到這兩個功能views.py最初加載模板和功能在views.py處理來自模板提交。

另外,僅供參考,這里有一些其他鏈接討論同樣的問題

安裝 django-livereload-server 后,在某些頁面上也隨機出現此錯誤。 卸載 django-livereload-server 成功了。

我也遇到了這個問題,但老實說,幾分鍾后我在瀏覽器上刷新了,沒有做任何更改,當時它工作正常。 我的命令行中有此消息,因此它可能會提供有關導致問題的原因的線索:

Not Found: /css/reset/reset.css
[03/Jul/2020 20:52:13] "GET /css/reset/reset.css HTTP/......

DJANGO/AJAX 工作流程完整方法在這里:)

const url = "{% url 'YOUR_URL_NAME' pk=12345 %}".replace(/12345/, id.toString());
$.ajax({
        type: 'POST',
        url: url,
        data: {'id':id, "csrfmiddlewaretoken": '{{csrf_token}}'},
        beforeSend: function() { $('#response').text('Please wait ...'); },
        success: function (response) {
            console.log(response)           
        },
        error: function (response) {
            console.log(response)
        }
    })

希望它會起作用!!!

對我有用的是從我的settings.py注釋掉以下行

'django.middleware.csrf.CsrfViewMiddleware'

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM