Django使用dropzone.js上传图片报CSRF verification failed错误如何解决?
问题解决步骤
第一步:确认CSRF令牌获取逻辑正确
你当前使用的从meta标签取令牌的方式,前提是页面<head>中已经声明了对应的meta标签,若未添加可以选择以下两种方案二选一:
方案1:在页面<head>中添加meta标签<meta name="csrf-token" content="{{ csrf_token }}">方案2:直接从现有表单中取令牌,你表单里已经用了
{% csrf_token %}模板标签,会自动生成name为csrfmiddlewaretoken的隐藏输入框,直接取它的值更稳妥:const CSRF_TOKEN = document.querySelector('input[name="csrfmiddlewaretoken"]').value;第二步:确认请求头配置符合Django规范
Django默认识别的CSRF请求头键名为X-CSRFToken,你之前写的x-csrf-token虽然HTTP协议不区分头的大小写,但建议使用标准键名避免兼容问题。同时要确保headers配置放在Dropzone配置的根节点,不要错放到init等子配置项中,正确配置示例:
Dropzone.options.fileDropzone = { url: '/media/', // 注意headers放在配置根节点 headers: { 'X-CSRFToken': CSRF_TOKEN }, // 以下保留你原有配置即可 init: function() { this.on("error", function(file, message) { alert(message); this.removeFile(file); }); var submitBtn = document.querySelector("#submitBtn"); var myDropzone = this; submitBtn.addEventListener("click", function() { console.log("upload"); myDropzone.processQueue(); }) }, // 注意这里原来的autoprocessQueue拼写错误,正确为autoProcessQueue autoProcessQueue: true, clickable: true, thumbnailHeight: 90, thumbnailWidth: 115, maxFiles: 1, maxFilesize: 10, parallelUploads: 1, addRemoveLinks: true, dictRemoveFile: 'delete', uploadMultiple: false, }
- 第三步:备用方案(无需配置请求头)
如果不想处理请求头问题,可以直接把CSRF令牌加到POST请求参数中,Django也会优先校验请求参数里的csrfmiddlewaretoken字段,使用Dropzone的params配置即可:
Dropzone.options.fileDropzone = { url: '/media/', params: { csrfmiddlewaretoken: document.querySelector('input[name="csrfmiddlewaretoken"]').value }, // 其他原有配置不变... }
- 排查手段
如果以上配置都修改后仍报错,可以打开浏览器开发者工具的「网络」面板,找到提交的上传请求,查看请求头/请求体中是否携带了正确的CSRF值,和页面生成的令牌值对比是否一致,即可定位是未携带令牌还是令牌值错误的问题。
内容的提问来源于stack exchange,提问作者Hill S
相关产品推荐
相关产品推荐

