Hemos estado usando Mock para Python por un tiempo.
Ahora, tenemos una situación en la que queremos burlarnos de una función
def foo(self, my_param):
#do something here, assign something to my_result
return my_result
Normalmente, la forma de burlarse de esto sería (suponiendo que foo sea parte de un objeto)
self.foo = MagicMock(return_value="mocked!")
Incluso, si llamo a foo () un par de veces, puedo usar
self.foo = MagicMock(side_effect=["mocked once", "mocked twice!"])
Ahora, me enfrento a una situación en la que quiero devolver un valor fijo cuando el parámetro de entrada tiene un valor particular. Entonces, si digamos "my_param" es igual a "algo", entonces quiero devolver "my_cool_mock"
Esto parece estar disponible en mockito para python
when(dummy).foo("something").thenReturn("my_cool_mock")
¿He estado buscando cómo lograr lo mismo con Mock sin éxito?
¿Algunas ideas?
python
unit-testing
mocking
mockito
Juan Antonio Gómez Moriano
fuente
fuente
monkeypatch
. Monkeypatch es más para "reemplazar esta función en aras de la prueba", mientras que Mock es lo que usa cuando también desea verificarmock_calls
o hacer afirmaciones sobre cómo se llamó y así sucesivamente. Hay un lugar para ambos, y a menudo uso ambos en diferentes momentos en un archivo de prueba dado.Respuestas:
http://www.voidspace.org.uk/python/mock/mock.html#calling
fuente
side effect
es el término exacto: en.wikipedia.org/wiki/Side_effect_(computer_science)CallableMixin.side_effect
, sino que la función separada definida en el ejemplo tiene el mismo nombre.Como se indica en el objeto Python Mock con el método llamado varias veces
Una solución es escribir mi propio efecto secundario
Eso hace el truco
fuente
El efecto secundario toma una función (que también puede ser una función lambda ), por lo que para casos simples puede usar:
fuente
Terminé aquí buscando " cómo burlarse de una función basada en argumentos de entrada " y finalmente resolví esto creando una función auxiliar simple:
Ahora:
¡Espero que esto ayude a alguien!
fuente
También puede usar
partial
desdefunctools
si desea usar una función que toma parámetros pero la función de la que se está burlando no. Por ejemplo, así:Esto devolverá un invocable que no acepta parámetros (como timezone.now () de Django), pero mi función mock_year sí.
fuente
got multiple values for argument
.Solo para mostrar otra forma de hacerlo:
fuente
También puedes usar
@mock.patch.object
:Digamos que un módulo
my_module.py
usapandas
para leer desde una base de datos y nos gustaría probar este módulo mediante unpd.read_sql_table
método de burla (que tomatable_name
como argumento).Lo que puede hacer es crear (dentro de su prueba) un
db_mock
método que devuelva diferentes objetos según el argumento proporcionado:En tu función de prueba, entonces haces:
fuente
Si "desea devolver un valor fijo cuando el parámetro de entrada tiene un valor particular" , tal vez ni siquiera necesita un simulacro y podría usar un
dict
junto con suget
método:Esto funciona bien cuando la salida de tu falso es un mapeo de entrada. Cuando es una función de entrada, sugiero usar
side_effect
según la respuesta de Amber .También puede usar una combinación de ambos si desea preservar
Mock
las capacidades (assert_called_once
,call_count
etc.):fuente
Sé que es una pregunta bastante antigua, podría ayudar como una mejora usando Python Lamdba
fuente