Як надсилати запити за допомогою JSON в модульних тестах


96

У мене є код у програмі Flask, який використовує JSON у запиті, і я можу отримати об'єкт JSON приблизно так:

Request = request.get_json()

Це працює нормально, однак я намагаюся створити модульні тести, використовуючи модуль unittest Python, і мені важко знайти спосіб надіслати JSON із запитом.

response=self.app.post('/test_function', 
                       data=json.dumps(dict(foo = 'bar')))

Це дає мені:

>>> request.get_data()
'{"foo": "bar"}'
>>> request.get_json()
None

Здається, у Flask є аргумент JSON, де ви можете встановити json = dict (foo = 'bar') у запиті на повідомлення, але я не знаю, як це зробити з модулем unittest.


Що request.dataмістить? Часто, коли синтаксичний аналіз json не вдається через неправильне введення, він не вдається безшумно і повертає, Noneтаким чином, вихідні дані можуть бути не json.
Benoît Latinier

>>> request.get_data () '{"foo": "bar"}' >>> request.get_json () None Я не зовсім впевнений, як працює запит flask, але, схоже, дані та json відокремлюються не може зрозуміти, як надсилати інформацію до json, а не до даних, якщо це має сенс.
Sepehr Nazari

9
я думаю, що це заголовки типу вмісту, спробуйте встановити для них appliacation / json. також параметр force корисний, але ви, мабуть, не хочете їхати туди лише для того, щоб пройти unittests, краще змінити mime
user3012759

Відповіді:


194

Зміна посади на

response=self.app.post('/test_function', 
                       data=json.dumps(dict(foo='bar')),
                       content_type='application/json')

це виправили.

Завдяки користувачеві3012759.


руйнував мені голову. Не розумію, чому вам потрібно скидати дані, коли ви вже вказуєте application/jsonтип вмісту.
dimmg

Я вважаю, що це тому, що все, що ви надсилаєте в дописі, має бути рядком.
Sepehr Nazari,

17
Вражаюче, цього немає в документах, оскільки flask test_client не має документів API!
rjurney

Як отримати дані з відповіді?
змінна

@variable, з відповіддю на post запит, як resp = client.post('/my/endpoint/',json=my_json_data)ви можете отримати доступ до даних у вигляді байтів resp.data.
amiabl

44

ОНОВЛЕННЯ: Оскільки випущені flask.testing.FlaskClientметоди Flask 1.0 приймають jsonаргументи та Response.get_jsonдодані методи, див. Приклад .

для колби 0.x ви можете використовувати квитанцію нижче:

from flask import Flask, Response as BaseResponse, json
from flask.testing import FlaskClient
from werkzeug.utils import cached_property


class Response(BaseResponse):
    @cached_property
    def json(self):
        return json.loads(self.data)


class TestClient(FlaskClient):
    def open(self, *args, **kwargs):
        if 'json' in kwargs:
            kwargs['data'] = json.dumps(kwargs.pop('json'))
            kwargs['content_type'] = 'application/json'
        return super(TestClient, self).open(*args, **kwargs)


app = Flask(__name__)
app.response_class = Response
app.test_client_class = TestClient
app.testing = True

1
І не забувайте, що аргумент json повинен бути dictне рядком JSON!
LaundroMat
Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.