Comment obtenir posté json dans Flask?

j'essaye de construire une API simple en utilisant un flacon, dans lequel je veux maintenant lire quelques JSON postés. Je fais le post avec le Postman Chrome extension , et le JSON I post est tout simplement {"text":"lalala"} . J'essaie de lire le JSON en utilisant la méthode suivante:

@app.route('/api/add_message/<uuid>', methods=['GET', 'POST'])
def add_message(uuid):
    content = request.json
    print content
    return uuid

sur le navigateur il renvoie correctement l'uuid que j'ai mis dans L'GET, mais sur la console, il imprime juste None (où je m'attends à ce qu'il imprime le {"text":"lalala"} . Faire quelqu'un sait comment je peux obtenir le JSON posté à partir de la méthode Flask?

183
demandé sur Martijn Pieters 2013-11-15 16:35:19

4 réponses

vous devez définir le type de contenu de la requête à application/json pour que la propriété .json fonctionne; sinon, ce sera None . Voir la fiole Request documentation :

si le type MIME est application/json , il contiendra les données JSON analysées. Sinon, ce sera None .

fiole 0.10 a ajouté le request.get_json() méthode , et vous devrait utiliser cette méthode au lieu de la propriété .json . Vous pouvez dire à la méthode de sauter l'exigence de type de contenu en définissant force=True .

notez que si une exception est soulevée à ce point( pouvant donner lieu à une mauvaise réponse de demande de 400), votre JSON data est invalide. Il est en quelque sorte malformé; vous pouvez le vérifier avec un validateur JSON.

264
répondu Martijn Pieters 2017-11-05 12:25:39

pour référence, voici le code complet pour envoyer json depuis un client Python:

import requests
res = requests.post('http://localhost:5000/api/add_message/1234', json={"mytext":"lalala"})
if res.ok:
    print res.json()

l'entrée "json=" définira automatiquement le type de contenu, comme expliqué ici: Post JSON utilisant les requêtes Python

et le client ci-dessus fonctionnera avec ce code côté serveur:

from flask import Flask, request, jsonify
app = Flask(__name__)

@app.route('/api/add_message/<uuid>', methods=['GET', 'POST'])
def add_message(uuid):
    content = request.json
    print content['mytext']
    return jsonify({"uuid":uuid})

if __name__ == '__main__':
    app.run(host= '0.0.0.0',debug=True)
45
répondu Luke 2017-05-23 12:10:48

C'est la façon dont je voudrais le faire et il doit être

@app.route('/api/add_message/<uuid>', methods=['GET', 'POST'])
def add_message(uuid):
    content = request.get_json(silent=True)
    print content
    return uuid

avec silent=True , la fonction get_json échouera silencieusement en essayant de récupérer le corps json. Par défaut, il est défini à False . Le réglage de force=True ignorera la vérification de request.headers.get('Content-Type') == 'application/json' que le flacon fait pour vous. Par défaut, cela est aussi défini à False . Voir documentation du flacon .

je recommande fortement en laissant force=False et en faisant envoyer par le client l'en-tête Content-Type pour le rendre plus explicite.

Espérons que cette aide!

42
répondu radtek 2015-10-27 22:11:47

Cette solution fonctionne:

from flask import Flask, request, jsonify

app = Flask(__name__)


@app.route('/hello', methods=['POST'])
def hello():
   return jsonify(request.json)
5
répondu trojek 2017-02-28 15:40:43