David Crook David Crook - 3 months ago 23
JSON Question

Flask receiving Post Json

I'm working on a flask web application in which the client posts data to the server in the form of:

{
"sess_id" : 1 ,
"annotations" :
[ {"tag_start" : "TIME","tag_end" : "TIME","tag" : "YOUR_TAG"}, {"tag_start" : "TIME","tag_end" : "TIME","tag" : "YOUR_TAG"}, {"tag_start" : "TIME","tag_end" : "TIME","tag" : "YOUR_TAG"}]
}

Here is the full Ajax post...

$.ajax({
url: 'http://127.0.0.1:5000/api/saveannotation',
type: 'POST',
headers: {'Content-Type' : 'application/json'},
data: {'sess_id' : $('#sessionid_area').val(),
'annotations': JSON.parse(annotations)},
success: function(data) { alert(data.status); }
});


so I can even see this on the api side, which is defined as such:

@sessionapis.route('/saveannotation', methods=['GET', 'POST'])
@login_required
def save_annotation():
rData = request.data
if request.method == 'GET':
return jsonify({'status' : 'success GET'})
else:
return jsonify({'status' : 'success'})


The issue is that data is a "byte" type, not a dict. I also can't call request.json or request.get_json(silent=True), it returns "400 bad request".

Here is a sample of what is in request.data:

b'sess_id=1&annotations%5B0%5D%5Btag_start%5D=2...


it appears to be url encoded for some reason. Values is also empty. If I choose to do something wild, like leave out the content-type = json; I can get a dict-like thing, but I have to access it very oddly. I don't get individual objects, but rather just flat access to all properties.

Any thoughts on how to just get the json parsed into a reasonable object?

Thanks for any hints!

Answer

Just passing a content-type header of JSON doesn't actually make the data itself into JSON. You either need to do that yourself, or tell jQuery to do so.

$.ajax({
    url: 'http://127.0.0.1:5000/api/saveannotation',
    type: 'POST',
    contentType: 'application/json',
    data: JSON.stringify({'sess_id' : $('#sessionid_area').val(),
        'annotations': JSON.parse(annotations)}),
    success: function(data) { alert(data.status); }
});

Now your data will be in JSON format and you can get it as a Python dict with request.get_json().