无法打开 CSRF 的请求 JSON

Cannot unpack request JSON with CSRF on

Ajax请求只要设置@csrf.exempt就可以解包。一旦我将其注释掉,request.get_json(force=True) 就会失败。将其通过调试器: (Pdb) p request._cached_json 'Request' object has no attribute '_cached_json' 模板代码:

var csrf_token = "{{ csrf_token() }}";
$.ajaxSetup({
    beforeSend: function(xhr, settings) {
        if (!/^(GET|HEAD|OPTIONS|TRACE)$/i.test(settings.type) && !this.crossDomain) {
            xhr.setRequestHeader("X-CSRFToken", csrf_token);
        }}});

正在分派请求:

save()
{
    $.post("/save", JSON.stringify({'name': 'aaa'}), accept_reply, "json");
} 

Flask 处理请求:

@app.route('/save', methods=("POST",))
#@csrf.exempt
def save():
    order_data = request.get_json(force=True)
    return jsonify({"status": "ok"})

@csrf.exempt被注释掉时,request没有属性_cached_jsonrequest.get_json(force=True)引发异常,而request.get_json()只是returnsNone。

这里的问题是 Flask 需要一个 "Content-Type": "application/json" header 来识别你正在发布一个 JSON 包,否则我相信它认为你'重新发送 urlencoded 表单数据。

我发现如果我正在寻找 POST JSON 数据到 Flask,我不能使用任何 jQuery "convenience" AJAX 方法.

试试这个:

$.ajax({
    type: "POST",
    url: "{{ url_for('.update_formulary_mb') }}",
    contentType: "application/json",
    data: JSON.stringify({id: state.config, update: records}),
    dataType: "json",
    success: function(response) {
        console.log(response);
    },
    error: function(err) {
        console.log(err);
    },
});

编辑 2017 年 9 月 1 日

事实证明,如果您的所有 XHR 请求都需要使用 jQuery 的相同参数,您 可以 使用 jQuery post() 方法s ajaxSetup() 方法:

$.ajaxSetup({
    contentType: "application/json"
});

这会将通用参数传递给 all ajax 以及其使用范围内的派生方法...所以如果您遵循相同的方法,它会很好地工作页面上所有 XHR 调用的模式...