如何将 Django 的 CSRF 令牌添加到 jQuery POST 请求的 header?
How to add Django's CSRF token to the header of a jQuery POST request?
我正在尝试制作一个带有动态 pre-populated 字段的 Django 表单:也就是说,当一个字段 (checkin_type
) 从 drop-down 中得到 selected 时菜单,其他字段自动获得 pre-populated 和相应的数据。为此,我想在 drop-down 选项被 select 编辑后立即向服务器发送 POST 请求。
到目前为止,我已经尝试了以下模板(在 https://docs.djangoproject.com/en/2.0/ref/csrf/ 之后):
<script src="https://ajax.googleapis.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<script src="https://cdn.jsdelivr.net/npm/js-cookie@2/src/js.cookie.min.js"></script>
<script>
$(document).ready(function(){
var csrftoken = Cookies.get('csrftoken');
$(".auto-submit").change(function() {
$.post({
url: "{% url 'get-checkin-type' %}",
data: $(".auto-submit option:selected").val(),
headers: {
X-CSRFToken: csrftoken
}
})
});
});
</script>
<form action="" method="post">{% csrf_token %}
{% for field in form %}
<div class="{% if field.name == 'checkin_type' %}auto-submit{% endif %}">
{{ field.errors }}
{{ field.label_tag }}
{{ field }}
</div>
{% endfor %}
<input type="submit" value="Send message" />
</form>
然而,当我 select 一个 drop-down 选项时,我得到一个
new:17 Uncaught SyntaxError: Unexpected token -
来自 X-CSRFToken: csrftoken
行:
有人可以指出这段代码有什么问题吗? (我尝试从 https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Errors/Unexpected_token 查找它,但到目前为止无法弄清楚)。
顺便说一句,从 看来,也可以将 CSRF 令牌添加到 POST 请求的 data
,但这似乎不是最优雅的方法对我来说,文档说明
For this reason, there is an alternative method: on each XMLHttpRequest, set a custom X-CSRFToken header to the value of the CSRF token.
您缺少单引号,请按以下方式尝试。
$(".auto-submit").change(function() {
$.post({
url: "{% url 'get-checkin-type' %}",
data: $(".auto-submit option:selected").val(),
headers: {
'X-CSRFToken': csrftoken
}
})
});
PSK's solution works, but for the sake of completeness, here is the approach as outlined by the Django docs after reading a bit further (from https://docs.djangoproject.com/en/2.0/ref/csrf/#setting-the-token-on-the-ajax-request) 它使用 .ajaxSetup
一劳永逸地覆盖所有请求:
<script src="https://ajax.googleapis.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<script src="https://cdn.jsdelivr.net/npm/js-cookie@2/src/js.cookie.min.js"></script>
<script>
$(document).ready(function(){
var csrftoken = Cookies.get('csrftoken');
function csrfSafeMethod(method) {
// these HTTP methods do not require CSRF protection
return (/^(GET|HEAD|OPTIONS|TRACE)$/.test(method));
}
$.ajaxSetup({
beforeSend: function(xhr, settings) {
if (!csrfSafeMethod(settings.type) && !this.crossDomain) {
xhr.setRequestHeader("X-CSRFToken", csrftoken);
}
}
});
$(".auto-submit").change(function() {
$.post({
url: "{% url 'get-checkin-type' %}",
data: $(".auto-submit option:selected").val(),
})
});
});
</script>
我正在尝试制作一个带有动态 pre-populated 字段的 Django 表单:也就是说,当一个字段 (checkin_type
) 从 drop-down 中得到 selected 时菜单,其他字段自动获得 pre-populated 和相应的数据。为此,我想在 drop-down 选项被 select 编辑后立即向服务器发送 POST 请求。
到目前为止,我已经尝试了以下模板(在 https://docs.djangoproject.com/en/2.0/ref/csrf/ 之后):
<script src="https://ajax.googleapis.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<script src="https://cdn.jsdelivr.net/npm/js-cookie@2/src/js.cookie.min.js"></script>
<script>
$(document).ready(function(){
var csrftoken = Cookies.get('csrftoken');
$(".auto-submit").change(function() {
$.post({
url: "{% url 'get-checkin-type' %}",
data: $(".auto-submit option:selected").val(),
headers: {
X-CSRFToken: csrftoken
}
})
});
});
</script>
<form action="" method="post">{% csrf_token %}
{% for field in form %}
<div class="{% if field.name == 'checkin_type' %}auto-submit{% endif %}">
{{ field.errors }}
{{ field.label_tag }}
{{ field }}
</div>
{% endfor %}
<input type="submit" value="Send message" />
</form>
然而,当我 select 一个 drop-down 选项时,我得到一个
new:17 Uncaught SyntaxError: Unexpected token -
来自 X-CSRFToken: csrftoken
行:
有人可以指出这段代码有什么问题吗? (我尝试从 https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Errors/Unexpected_token 查找它,但到目前为止无法弄清楚)。
顺便说一句,从 data
,但这似乎不是最优雅的方法对我来说,文档说明
For this reason, there is an alternative method: on each XMLHttpRequest, set a custom X-CSRFToken header to the value of the CSRF token.
您缺少单引号,请按以下方式尝试。
$(".auto-submit").change(function() {
$.post({
url: "{% url 'get-checkin-type' %}",
data: $(".auto-submit option:selected").val(),
headers: {
'X-CSRFToken': csrftoken
}
})
});
PSK's solution works, but for the sake of completeness, here is the approach as outlined by the Django docs after reading a bit further (from https://docs.djangoproject.com/en/2.0/ref/csrf/#setting-the-token-on-the-ajax-request) 它使用 .ajaxSetup
一劳永逸地覆盖所有请求:
<script src="https://ajax.googleapis.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<script src="https://cdn.jsdelivr.net/npm/js-cookie@2/src/js.cookie.min.js"></script>
<script>
$(document).ready(function(){
var csrftoken = Cookies.get('csrftoken');
function csrfSafeMethod(method) {
// these HTTP methods do not require CSRF protection
return (/^(GET|HEAD|OPTIONS|TRACE)$/.test(method));
}
$.ajaxSetup({
beforeSend: function(xhr, settings) {
if (!csrfSafeMethod(settings.type) && !this.crossDomain) {
xhr.setRequestHeader("X-CSRFToken", csrftoken);
}
}
});
$(".auto-submit").change(function() {
$.post({
url: "{% url 'get-checkin-type' %}",
data: $(".auto-submit option:selected").val(),
})
});
});
</script>