简体   繁体   English

Django 后端、React 前端和 CSRF Post

[英]Django backend, React frontend and CSRF Post

In my cenario I am using a form in my react frontend ( http://localhost:3000/submit ) to post to my url http://localhost:8000/api/submit/在我的场景中,我在我的反应前端( http://localhost:3000/submit )中使用一个表单来发布到我的 url http://localhost:8000/api/submit/

However, I have received this response:但是,我收到了这样的回复:

"detail": "CSRF Failed: CSRF token missing or incorrect." "detail": "CSRF 失败:CSRF 令牌丢失或不正确。"

My class view is something like that:我的班级观点是这样的:

from rest_framework.views import APIView
from rest_framework.parsers import MultiPartParser, FormParser

class Submit(APIView):
    parser_classes = (MultiPartParser, FormParser)
    def post(self, request, *args, **kwargs):
        #custom post

I have two questions:我有两个问题:

  1. How do I decorate dispatch() to exempt csrf?如何装饰 dispatch() 以免除 csrf?
  2. How can I provide CSRF to my frontend?如何向我的前端提供 CSRF?

** **

SOLUTION by Risadinha : Risadinha 的解决方案:

** **

import cookie from "react-cookies";

...

<input
 type="hidden"
 value={cookie.load("csrftoken")}
 name="csrfmiddlewaretoken"
/>

You need to set both the cookie and the header to the CSRF token as transmitted during the initial call wich loads the react page.您需要将 cookie 和标头都设置为在加载反应页面的初始调用期间传输的 CSRF 令牌。

Basically you need to read the value of the cookie "csrftoken" as transmitted from the Django server and set that as the value of the header "X-CSRFTOKEN" for all the post AJAX requests in your react app.基本上,您需要读取从 Django 服务器传输的 cookie "csrftoken" 的值,并将其设置为响应应用程序中所有 post AJAX 请求的标头 "X-CSRFTOKEN" 的值。 Best done generally (index.js for example).通常最好完成(例如 index.js)。

Example using axios (we are using graphql) client in React:在 React 中使用 axios(我们使用的是 graphql)客户端的示例:

import axios from "axios";
import cookie from "react-cookies";

axios.defaults.xsrfCookieName = "csrftoken";
axios.defaults.xsrfHeaderName = "X-CSRFTOKEN";

your_client.setHeaders({"X-CSRFTOKEN": cookie.load("csrftoken")});

Without ajax, add the cookie's value to the form like this - if you cannot use the template tag {% csrf_token %} (in a react form):如果没有 ajax,像这样将 cookie 的值添加到表单中 - 如果您不能使用模板标签{% csrf_token %} (以反应形式):

<input type="hidden" name="csrfmiddlewaretoken" value="{value-of-the-cookie}" /> 

The documentation: https://docs.djangoproject.com/en/3.1/ref/csrf/文档: https : //docs.djangoproject.com/en/3.1/ref/csrf/

This seems a bit hacky but you can get the csrf token in a view with the django.middleware.csrf.get_token() method.这看起来有点麻烦,但您可以使用django.middleware.csrf.get_token()方法在视图中获取 csrf 令牌。 So I would make a view like this:所以我会提出这样的观点:

from django.http import JsonResponse

def get_csrf(request):
    csrf_token = django.middleware.csrf.get_token()
    return JsonResponse({'csrf_token':csrf_token})

Of course you want to protect this request so anyone can't grab the token.当然,您希望保护此请求,以便任何人都无法获取令牌。 Which seems to defeat the purpose of it anyway...无论如何,这似乎违背了它的目的......

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM