Возврат ответа JSON из представления Flask

464

У меня есть функция, которая анализирует CSV-файл с помощью Pandas и выдает отчет со сводной информацией. Я хочу вернуть результаты как ответ от представления Flask. Как вернуть ответ JSON?

@app.route("/summary")
def summary():
    d = make_summary()
    # send it back as json
Код ниндзя
источник

Ответы:

753

Передайте сводные данные в jsonifyфункцию, которая возвращает ответ JSON.

from flask import jsonify

@app.route('/summary')
def summary():
    d = make_summary()
    return jsonify(d)

Начиная с Flask 0.11, вы можете передавать любой JSON-сериализуемый тип, а не просто dict, как объект верхнего уровня.

codegeek
источник
4
Начиная с Flask 1.1.0 , теперь вы можете напрямую возвращать python dict, и он будет автоматически jsonify'd от Flask.
Адриен Болл
204

jsonifyсериализует данные, которые вы передаете в JSON. Если вы хотите сериализовать данные самостоятельно, сделайте то, что jsonifyделает, создав ответ с помощью status=200и mimetype='application/json'.

from flask import json

@app.route('/summary')
def summary():
    data = make_summary()
    response = app.response_class(
        response=json.dumps(data),
        status=200,
        mimetype='application/json'
    )
    return response
SCLS
источник
129

Передайте аргументы ключевых слов, flask.jsonifyи они будут выведены в виде объекта JSON.

@app.route('/_get_current_user')
def get_current_user():
    return jsonify(
        username=g.user.username,
        email=g.user.email,
        id=g.user.id
    )
{
    "username": "admin",
    "email": "admin@localhost",
    "id": 42
}

Если у вас уже есть диктат, вы можете передать его напрямую как jsonify(d).

zengr
источник
1
Согласно примечаниям к выпуску 1.1.0 , Flask позволяет возвращать словарь из функции просмотра. Подобно тому, как возвращение строки приведет к ответу text / html, возвращение dict вызовет jsonify для получения ответа application / json,
CodeMantle
34

Если вы не хотите использовать jsonifyпо какой-либо причине, вы можете сделать то, что он делает вручную. Вызовите flask.json.dumpsдля создания данных JSON, а затем верните ответ с application/jsonтипом содержимого.

from flask import json

@app.route('/summary')
def summary():
    data = make_summary()
    response = app.response_class(
        response=json.dumps(data),
        mimetype='application/json'
    )
    return response

flask.jsonотличается от встроенного jsonмодуля. Он будет использовать более быстрый simplejsonмодуль, если он доступен, и разрешает различные интеграции с вашим приложением Flask.

Энтони Авули
источник
17

Если вы хотите проанализировать файл, загруженный пользователем, быстрый старт Flask покажет, как получить файлы от пользователей и получить к ним доступ. Получить файл request.filesи передать его в функцию сводки.

from flask import request, jsonify
from werkzeug import secure_filename

@app.route('/summary', methods=['GET', 'POST'])
def summary():
    if request.method == 'POST':
        csv = request.files['data']
        return jsonify(
            summary=make_summary(csv),
            csv_name=secure_filename(csv.filename)
        )

    return render_template('submit_data.html')

Замените 'data'ключ на request.filesименем файла, введенного в вашу HTML-форму.

teechap
источник
13

Чтобы вернуть ответ JSON и установить код состояния, вы можете использовать make_response:

from flask import jsonify, make_response

@app.route('/summary')
def summary():
    d = make_summary()
    return make_response(jsonify(d), 200)

Вдохновение взято из этого комментария в трекере Flask.

рубль
источник
10

Я использую декоратор, чтобы вернуть результат jsonfiy. Я думаю, что это более читабельно, когда представление имеет несколько возвращений. Это не поддерживает возврат типа кортежа content, status, но app.errorhandlerвместо этого я обрабатываю возвращение статусов ошибок .

import functools
from flask import jsonify

def return_json(f):
    @functools.wraps(f)
    def inner(**kwargs):
        return jsonify(f(**kwargs))

    return inner

@app.route('/test/<arg>')
@return_json
def test(arg):
    if arg == 'list':
        return [1, 2, 3]
    elif arg == 'dict':
        return {'a': 1, 'b': 2}
    elif arg == 'bool':
        return True
    return 'none of them'
иман
источник
4

До Flask 0.11 jsonfiyне разрешал бы возвращать массив напрямую. Вместо этого передайте список в качестве аргумента ключевого слова.

@app.route('/get_records')
def get_records():
    results = [
        {
          "rec_create_date": "12 Jun 2016",
          "rec_dietary_info": "nothing",
          "rec_dob": "01 Apr 1988",
          "rec_first_name": "New",
          "rec_last_name": "Guy",
        },
        {
          "rec_create_date": "1 Apr 2016",
          "rec_dietary_info": "Nut allergy",
          "rec_dob": "01 Feb 1988",
          "rec_first_name": "Old",
          "rec_last_name": "Guy",
        },
    ]
    return jsonify(results=list)
mania_device
источник
2

В Flask 1.1, если вы возвращаете словарь, и он будет автоматически преобразован в JSON. Так что, если make_summary()возвращает словарь, вы можете

from flask import Flask

app = Flask(__name__)

@app.route('/summary')
def summary():
    d = make_summary()
    return d

SO , который просит о включении код состояния был закрыт в двух экземплярах на этот. Таким образом, чтобы также ответить на этот вопрос, вы можете включить код состояния, возвращая кортеж формы (dict, int). dictПреобразуется в формат JSON и intбудет HTTP Status Code. Без какого-либо ввода Status является значением по умолчанию 200. Таким образом, в приведенном выше примере код будет 200. В приведенном ниже примере он изменяется на 201.

from flask import Flask

app = Flask(__name__)

@app.route('/summary')
def summary():
    d = make_summary()
    return d, 201  # 200 is the default

Вы можете проверить код состояния, используя

curl --request GET "http://127.0.0.1:5000/summary" -w "\ncode: %{http_code}\n\n"
Стивен Хоуэлл
источник
0

если это диктует, колба может вернуть его напрямую (версия 1.0.2)

def summary():
    d = make_summary()
    return d, 200
c8999c 3f964f64
источник
0

"" " Использование Flask Class-base View " ""

from flask import Flask, request, jsonify

from flask.views import MethodView

app = Flask(**__name__**)

app.add_url_rule('/summary/', view_func=Summary.as_view('summary'))

class Summary(MethodView):

    def __init__(self):
        self.response = dict()

    def get(self):
        self.response['summary'] = make_summary()  # make_summary is a method to calculate the summary.
        return jsonify(self.response)
Маниш Шарма
источник
0

Колба 1.1.x

Теперь запрос поддержки Flask возвращается напрямую через json, jsonify больше не требуется.

@app.route("/")
def index():
    return {
        "api_stuff": "values",
    }

эквивалентно

@app.route("/")
def index():
    return jsonify({
        "api_stuff": "values",
    })

для получения дополнительной информации читайте здесь https://medium.com/octopus-wealth/returning-json-from-flask-cf4ce6fe9aeb и https://github.com/pallets/flask/pull/3111.

Saifee
источник