Cómo enviar solicitudes con JSON en pruebas unitarias


96

Tengo un código dentro de una aplicación Flask que usa JSON en la solicitud, y puedo obtener el objeto JSON así:

Request = request.get_json()

Esto ha funcionado bien, sin embargo, estoy tratando de crear pruebas unitarias usando el módulo unittest de Python y tengo dificultades para encontrar una manera de enviar un JSON con la solicitud.

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

Esto me da:

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

Flask parece tener un argumento JSON en el que puede establecer json = dict (foo = 'bar') dentro de la solicitud de publicación, pero no sé cómo hacerlo con el módulo unittest.


¿Qué request.datacontiene? A menudo, cuando el análisis json falla debido a una entrada incorrecta, falla silenciosamente y regresa, por Nonelo que los datos de entrada sin procesar pueden no ser json.
— Benoît Latinier

>>> request.get_data () '{"foo": "bar"}' >>> request.get_json () Ninguno No estoy muy seguro de cómo funciona la solicitud de flask, pero parece separar datos y json, y yo No puedo averiguar cómo enviar información al json en lugar de los datos, si eso tiene algún sentido.
— Sepehr Nazari

9
Creo que son los encabezados de tipo de contenido, intente configurarlos en appliacation / json. también el parámetro de fuerza es útil, pero probablemente no quiera ir allí solo para hacer que pasen las
— pruebas unitarias

Respuestas:


194

Cambiando la publicación a

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

arreglado.

Gracias a user3012759.


estaba destrozando mi cabeza con esto. No entiendo por qué tiene que volcar los datos cuando ya está especificando el application/jsontipo de contenido.
— dimmg el

Creo que es porque todo lo que envías en una publicación tiene que ser una cadena.
— Sepehr Nazari

17
Increíble, esto no está en los documentos, ¡porque test_client de flask no tiene documentos API!
— rjurney

¿Cómo obtener datos de la respuesta?
— variable

@variable, con una respuesta de una post solicitud como resp = client.post('/my/endpoint/',json=my_json_data)si pudiera acceder a los datos como bytes con resp.data.
— amiabl

44

ACTUALIZACIÓN: Dado que los flask.testing.FlaskClientmétodos lanzados por Flask 1.0 aceptan jsonargumentos y Response.get_jsonmétodos agregados, vea el ejemplo .

para Flask 0.x puede usar el recibo a continuación:

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
¡Y no olvide que el argumento json no debe ser una dictcadena JSON!
— LaundroMat
Al usar nuestro sitio, usted reconoce que ha leído y comprende nuestra Política de Cookies y Política de Privacidad.
Licensed under cc by-sa 3.0 with attribution required.