Si vous voulez vraiment avoir plusieurs Unitttest, vous avez besoin de plusieurs méthodes. La seule façon d'obtenir cela est à travers une sorte de génération de code. Vous pouvez le faire à travers un métaclasses ou en modifiant légèrement la classe après la définition, y compris (si vous utilisez Python 2.6) par un décorateur de classe.
Voici une solution qui recherche les membres spéciaux 'multitest' et 'multitest_values' et les utilise pour construire les méthodes de test à la volée. Pas élégant, mais il fait à peu près ce que vous voulez:
import unittest
import inspect
class SomeValue(object):
def __eq__(self, other):
return other in [1, 3, 4]
class ExampleTestCase(unittest.TestCase):
somevalue = SomeValue()
multitest_values = [1, 2, 3, 4]
def multitest(self, n):
self.assertEqual(self.somevalue, n)
multitest_gt_values = "ABCDEF"
def multitest_gt(self, c):
self.assertTrue(c > "B", c)
def add_test_cases(cls):
values = {}
functions = {}
# Find all the 'multitest*' functions and
# matching list of test values.
for key, value in inspect.getmembers(cls):
if key.startswith("multitest"):
if key.endswith("_values"):
values[key[:-7]] = value
else:
functions[key] = value
# Put them together to make a list of new test functions.
# One test function for each value
for key in functions:
if key in values:
function = functions[key]
for i, value in enumerate(values[key]):
def test_function(self, function=function, value=value):
function(self, value)
name ="test%s_%d" % (key[9:], i+1)
test_function.__name__ = name
setattr(cls, name, test_function)
add_test_cases(ExampleTestCase)
if __name__ == "__main__":
unittest.main()
Ceci est la sortie quand je le lance
% python stackoverflow.py
.F..FF....
======================================================================
FAIL: test_2 (__main__.ExampleTestCase)
----------------------------------------------------------------------
Traceback (most recent call last):
File "stackoverflow.py", line 34, in test_function
function(self, value)
File "stackoverflow.py", line 13, in multitest
self.assertEqual(self.somevalue, n)
AssertionError: <__main__.SomeValue object at 0xd9870> != 2
======================================================================
FAIL: test_gt_1 (__main__.ExampleTestCase)
----------------------------------------------------------------------
Traceback (most recent call last):
File "stackoverflow.py", line 34, in test_function
function(self, value)
File "stackoverflow.py", line 17, in multitest_gt
self.assertTrue(c > "B", c)
AssertionError: A
======================================================================
FAIL: test_gt_2 (__main__.ExampleTestCase)
----------------------------------------------------------------------
Traceback (most recent call last):
File "stackoverflow.py", line 34, in test_function
function(self, value)
File "stackoverflow.py", line 17, in multitest_gt
self.assertTrue(c > "B", c)
AssertionError: B
----------------------------------------------------------------------
Ran 10 tests in 0.001s
FAILED (failures=3)
Vous pouvez immédiatement voir certains des problèmes qui se produisent avec la génération de code. D'où vient "test_gt_1"? Je pourrais changer le nom pour le plus long "test_multitest_gt_1" mais quel test est 1? Mieux ici serait de commencer par _0 au lieu de _1, et peut-être dans votre cas, vous savez que les valeurs peuvent être utilisées comme un nom de fonction Python.
Je n'aime pas cette approche. J'ai travaillé sur des bases de code qui AutoGénéré méthodes d'essai (dans un cas, en utilisant un métaclasse) et a trouvé qu'il était beaucoup plus difficile de comprendre qu'il était utile. Lorsqu'un test a échoué, il était difficile de trouver la source de l'affaire de l'échec, et il était difficile de coller dans le code de débogage pour sonder la raison de l'échec. (Les échecs de débogage dans l'exemple que j'ai écrit ici n'est pas aussi difficile que l'approche spécifique de la métaclasse avec laquelle je devais travailler.)
Avez-vous trouvé une façon de le faire? Ou peut-être avez-vous trouvé un autre outil pour cette tâche? J'ai besoin d'un tel comportement non plus. – legesh
http://thebongtraveller.blogspot.sg/2015/12/art-of-unittest-writing-auto-generation.html Est-ce la même chose? –