Unittest setUp / tearDown para varias pruebas

118

¿Existe una función que se activa al principio / final de un escenario de pruebas? Las funciones setUp y tearDown se activan antes / después de cada prueba.

Normalmente me gustaría tener esto:

class TestSequenceFunctions(unittest.TestCase):

    def setUpScenario(self):
        start() #launched at the beginning, once

    def test_choice(self):
        element = random.choice(self.seq)
        self.assertTrue(element in self.seq)

    def test_sample(self):
        with self.assertRaises(ValueError):
            random.sample(self.seq, 20)
        for element in random.sample(self.seq, 5):
            self.assertTrue(element in self.seq)

    def tearDownScenario(self):
        end() #launched at the end, once

Por ahora, estos setup y tearDown son pruebas unitarias y se extienden en todos mis escenarios (que contienen muchas pruebas), una es la primera prueba, la otra es la última prueba.

cisne
fuente
6
¿Cual version? El módulo unittest se ha ampliado para incluir module_setup y module_teardown en Python 2.7.
S.Lott
3
2.7 también introdujo los métodos de clase setUpClass () y tearDownClass (), que le permitirían tener varias clases en el mismo archivo con su propia configuración y desmontaje por suite.
Per Fagrell

Respuestas:

132

A partir de 2.7 (según la documentación ) obtiene setUpClassy tearDownClassque se ejecutan antes y después de que se ejecuten las pruebas en una clase determinada, respectivamente. Alternativamente, si tiene un grupo de ellos en un archivo, puede usar setUpModuley tearDownModule( documentación ).

De lo contrario, lo mejor que puede hacer es crear su propio TestSuite derivado y anularlo run(). Todas las demás llamadas serían manejadas por el padre, y la ejecución llamaría a su código de configuración y desmontaje alrededor de una llamada al runmétodo del padre .

David H. Clements
fuente
71

Tengo el mismo escenario, para mí los métodos setUpClass y tearDownClass funcionan perfectamente

import unittest

class Test(unittest.TestCase):
    @classmethod
    def setUpClass(cls):
        cls._connection = createExpensiveConnectionObject()

    @classmethod
    def tearDownClass(cls):
        cls._connection.destroy()
V.Gupta
fuente
6
Esto debe actualizarse para que sea la respuesta aceptada porque muestra un ejemplo correcto y estas funciones TIENEN que ser métodos de clase para funcionar, lo cual no se menciona en la respuesta aceptada.
NuclearPeon
1

Para python 2.5, y cuando se trabaja con pydev, es un poco difícil. Parece que pydev no usa el conjunto de pruebas, pero busca todos los casos de prueba individuales y los ejecuta todos por separado.

Mi solución para esto fue usar una variable de clase como esta:

class TestCase(unittest.TestCase):
    runCount = 0

    def setUpClass(self):
        pass # overridden in actual testcases

    def run(self, result=None):
        if type(self).runCount == 0:
            self.setUpClass()

        super(TestCase, self).run(result)
        type(self).runCount += 1

Con este truco, cuando hereda de esto TestCase(en lugar de del original unittest.TestCase), también heredará el valor runCountde 0. Luego, en el método de ejecución, el valor runCountdel caso de prueba secundario se verifica y se incrementa. Esto deja la runCountvariable para esta clase en 0.

Esto significa setUpClassque solo se ejecutará una vez por clase y no una vez por instancia.

Todavía no tengo un tearDownClassmétodo, pero supongo que se podría hacer algo con ese contador.

sanderd17
fuente
0

Aquí hay un ejemplo: 3 métodos de prueba acceden a un recurso compartido, que se crea una vez, no por prueba.

import unittest
import random

class TestSimulateLogistics(unittest.TestCase):

    shared_resource = None

    @classmethod
    def setUpClass(cls):
        cls.shared_resource = random.randint(1, 100)

    @classmethod
    def tearDownClass(cls):
        cls.shared_resource = None

    def test_1(self):
        print('test 1:', self.shared_resource)

    def test_2(self):
        print('test 2:', self.shared_resource)

    def test_3(self):
        print('test 3:', self.shared_resource)
kadir malak
fuente