【问题标题】:getting error while submitting a form using post method使用 post 方法提交表单时出错
【发布时间】:2018-04-26 07:30:44
【问题描述】:

错误:CSRF 令牌丢失或不正确。想要传递令牌以提交不在 django 模板上的表单。

views.py

....
def post(self, request):
    form = self.form_class(request.POST or None, request.FILES or None)
    if form.is_valid():
        email = form.cleaned_data.get('email')
        user = authenticate(email=email)
        if user is None:
            form.save()
            message = 'Saved Successfully'
            return HttpResponse(message)
        else:
            message = 'User Exists'
            return HttpResponse(message)
    else:
        message = 'Invalid form data'
        return HttpResponse(message)
....

form.html

....
<h1>Register</h1>
<form class="newform" action="/api/register/" method='POST'enctype="multipart/form-data">
    <input type='hidden' name='csrfmiddlewaretoken' value="some token value" />
    ....
</form>
....

【问题讨论】:

    标签: python django api django-csrf


    【解决方案1】:

    CSRF(跨站点请求伪造)保护的重点是防止提交不是由同一站点提供的表单。如果您确实需要使用来自不同站点的表单来提供 html 页面,则必须禁用 CSRF 保护。如果您只需要手动创建表单并通过 Django 视图从同一站点提供它,则可以使用 JavaScript 填充 csrfmiddlewaretoken 字段。首先,按照 Django 文档中的描述从 cookie 中提取一个令牌:https://docs.djangoproject.com/en/2.0/ref/csrf/#ajax 然后您可以填充该字段。

    JQuery 示例:

    $(function() {
    // 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 = $.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');
    $('input[name=csrfmiddlewaretoken]').attr('value', crsftoken);
    });
    

    【讨论】:

    • 要么禁用它,要么使用此功能。对吗?
    • 如果您在同一个 Django 站点上通过 Django 视图(例如 TemplateView CBV)提供现成的 html,则如果 JS 将起作用,则此部分。否则,您将不得不禁用 CSRF 保护并使用其他保护机制,例如访问令牌。
    • 整个网页不是这个 django 应用程序的一部分。我应该如何以及在哪里使用这个 sn-p?实际上这个表单出现onclick事件并且存在于js文件中。
    • Django 强化了 CSRF 保护,旨在防止您想要完成的事情。在您的情况下,禁用 CSRF 保护并使用其他方法来防止未经授权的表单提交。
    【解决方案2】:

    在您的表单中使用 {% csrf_token %}:

    <form>
    {% csrf_token %}
    <input ... >
    </form>
    

    【讨论】:

    • {% csrf_token %} 在您必须渲染模板时使用。但是我没有使用任何模板。嗯,我试过了,不行。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2017-12-23
    • 2019-05-31
    • 1970-01-01
    • 2018-05-14
    • 2020-01-06
    • 2010-10-10
    相关资源
    最近更新 更多