【问题标题】:Django with html/js error - Forbidden (CSRF cookie not set.)带有 html/js 错误的 Django - 禁止(未设置 CSRF cookie。)
【发布时间】:2017-10-07 02:40:07
【问题描述】:

所以我使用 Chrome,Django 版本 1.9.6,python 2.7.13。

我正在尝试将原始数据(音频文件)从 html/js 发送到 django 服务器以从 .mp3 转换为 .wav 格式。

但是,它甚至无法访问未设置 CSRF cookie 的 views.py。错误。

我已经尝试了几乎所有可以在网上找到的东西。

我有以下views.py和index.html。

index.html

<!DOCTYPE html>
<html lang="en-US">
<head>
    <meta charset="UTF-8">
    <link rel="stylesheet" href="https://www.w3schools.com/lib/w3.css">
    <title title="Audio Editor">Audio Editor</title>
    <script src="https://ajax.googleapis.com/ajax/libs/jquery/3.1.1/jquery.min.js"></script>
</head>
<main>
  <h1><img src="http://blog.blogtalkradio.com/wp-content/uploads/2011/10/Audio_Icon.jpg" alt="http://blog.blogtalkradio.com/wp-content/uploads/2011/10/Audio_Icon.jpg" style="float:left;width:30px;height:width;"><img src="https://image.freepik.com/free-icon/question-mark_318-52837.jpg" alt="https://image.freepik.com/free-icon/question-mark_318-52837.jpg" style="float:left;width:30px;height:width;"> Obfuscate your audio</h1>
  <br>
  <br>
  <body>
  <h3>1. Upload your audio:</h3>
  <input type="file" id="audio-file" onchange="fileAdded()"/>
  <p id="message"></p>
  <br>
  <h3>2. Obfuscate and download:</h3>
  <button id="obfuscate-button" onclick="obfuscate()">Obfuscate!</button>
  </body>
  <br>
  <br>
  <hr>
  <a href="https://github.com/mgjo5899/web_audio">Check out the github page!</a>
</main>

<script>
var file = undefined;
var audio_formats = ["mp3", "wav"];

// 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 = 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;
}

function fileAdded() {
  var x = document.getElementById("audio-file");
  file = x.files[0];
  var msg = document.getElementById("message");

  if (file != undefined) {
    x = file.name.split(".");
    var ext = x[x.length - 1];

    if (audio_formats.indexOf(ext) == -1) {
      msg.innerHTML = ext + " is not an audio file!";
    } else {
      msg.innerHTML = file.name + " has been successfully added!";
    }
  } else {
    msg.innerHTML = "Please select an audio file to obfuscate!";
  }
}

function obfuscate() {
  if (file == undefined)
    alert("Choose an audio file!");
  else {
    var obfuscateButton = document.getElementById("obfuscate-button");
    obfuscateButton.innerHTML = "Proccessing...";
    var xhr = new XMLHttpRequest();
    var url = "http://127.0.0.1:8000/obfuscator/obfuscate/";
    var method = 'POST';
    xhr.onreadystatechange = function() {
      if(xhr.readyState === 4 && xhr.status === 200) {
      	obfuscateButton.innerHTML = "Done!"
      }
    }
    xhr.open(method, url, true);

	xhr.setRequestHeader("X-CSRFToken", getCookie('csrftoken'));

    var formData = new FormData();
    formData.append("audio_file", file);
    formData.append("file_name", file.name)
    xhr.send(formData);
  }
}
</script>
</html>

view.py

from django.http import HttpResponse
from django.shortcuts import render
from django.views.decorators.csrf import ensure_csrf_cookie
from subprocess import call
from django.core.files import File
from .forms import UploadFileForm
from django.views.decorators.csrf import csrf_exempt
import subprocess

def index(request):
	return render(request, 'obfuscator/index.html')

#@csrf_exempt
def obfuscate(request):
	print("HI")
	if request.method == 'GET':
		return HttpResponse("Hi")

	if request.method == 'POST':
		print("files: " + str(request.FILES))
		print("posts: " + str(request.POST))

		if len(request.POST) > 0:
			handle_uploaded_file(request.FILES['audio_file'])

	return HttpResponse("The form was valid!")

def handle_uploaded_file(f):
	with open('temp.mp3', 'wb+') as destination:
		for chunk in f.chunks():
			destination.write(chunk)

	subprocess.check_call("ffmpeg -y -i temp.mp3 temp.wav", shell=True)

我真的不知道为什么这在我的计算机 (mac OS X) 上不起作用。 每次它给我(CSRF cookie not sets)错误,而不是(CSRF token 丢失或不正确。)错误。

我可以将它与 csrf_exempt 一起使用,但我想将它与 csrf 保护一起使用。

请帮忙!

谢谢。

【问题讨论】:

    标签: html django csrf


    【解决方案1】:

    确实,您的 CSRF 错误发生是因为您没有在模板中设置 csrf cookie

    您需要在模板中设置csrf_token,如下所示:

    <form action="#" method="POST">
        {% csrf_token %}
        <h3>1. Upload your audio:</h3>
        <input type="file" id="audio-file" onchange="fileAdded()"/>
        <p id="message"></p>
        <br>
        <h3>2. Obfuscate and download:</h3>
        <button id="obfuscate-button" onclick="obfuscate()">Obfuscate!   </button>
    </form>
    

    另一方面,也许您可​​以尝试在呈现模板的视图中使用 @ensure_csrf_cookie 装饰器

    @ensure_csrf_cookie
    def index(request):
        return render(request, 'obfuscator/index.html')
    

    【讨论】:

    • 我以为我是通过在打开后,在发送 ajax 发送之前执行 setRequestHeader("...") 在 javascript 部分中手动添加 csrf_token 的。你能确认一下吗?
    • 您获取和设置 cookie 以请求 heder 的方法是可以的,但是您需要创建 cookie,并且使用 django 您可以使用 csrf_token 标签或使用装饰器来完成
    • 是的,但不是只有当您直接使用html代码发送HTTP请求时?就像使用输入类型或类似的东西
    • 在呈现模板的视图中尝试使用@ensure_csrf_cookie
    • 不...不起作用。所以以前,我记得像您在 HTML 端(表单帖子)上建议的代码一样尝试它,并让 javascript 再次执行另一个 ajax 帖子。我首先认为它正在工作。然后意识到它为 JS AJAX 发布请求提供了错误,该请求被该表单 POST 请求对 HTML 的影响所覆盖。所以发送了两个不同的 post 请求,而 JS 部分没有工作,我想让它发生。
    猜你喜欢
    • 2012-05-03
    • 2016-11-26
    • 2021-10-08
    • 1970-01-01
    • 1970-01-01
    • 2022-09-27
    • 2020-01-16
    • 2014-03-11
    • 2021-06-22
    相关资源
    最近更新 更多