Bonjour sekitaka.
Aujourd'hui, je vais vous montrer comment tester une fonction qui utilise datetime.now ()
.
Par exemple, supposons que vous souhaitiez créer une fonction qui renvoie la chaîne "AAAAMMJJ" le lendemain après avoir exécuté un programme et tester cette fonction.
def get_tomorrow():
now_datetime = datetime.now()
tomorrow_datetime = now_datetime + timedelta(days=+1)
tomorrow = tomorrow_datetime.strftime("%Y%m%d")
return tomorrow
Tout d'abord, j'ai brièvement écrit le code de test suivant. Mais comme vous pouvez le voir, cela ne réussit que si vous exécutez le test le 22 juin 2017. Cela entraînera une erreur lors des tests quotidiens avec CI.
class Test(TestCase):
def test_get_tomorrow(self):
self.assertEqual("20170623", get_tomorrow())
L'idée suivante était de générer dynamiquement la valeur attendue. Cela passera le test chaque fois que vous le testerez. Cependant, en fait, j'ai écrit le même code que get_tomorrow, et j'ai l'impression qu'il n'a pas été testé.
class Test(TestCase):
def test_get_tomorrow(self):
expect_tomorrow = (datetime.now() + timedelta(days=+1)).strftime("%Y%m%d")
self.assertEqual(expect_tomorrow, get_tomorrow())
Par conséquent, j'ai pensé qu'il serait préférable de convertir datetime.now ()
en Mock, de renvoyer un datetime arbitraire et d'exécuter get_tomorrow
. Et j'ai écrit le code suivant.
from mock import Mock
class Test(TestCase):
def test_get_tomorrow(self):
datetime.now = Mock(return_value=datetime(year=2017, month=1, day=1))
self.assertEqual("20170102", get_tomorrow())
Quand je l'ai exécuté avec espoir, il semblait que je ne pouvais pas définir l'attribut sur la date / heure intégrée, donc je ne pouvais pas l'exécuter.
TypeError: can't set attributes of built-in/extension type 'datetime.datetime'
Quand j'étais en difficulté, j'ai trouvé une bibliothèque appelée freezegun qui se moquait du module datetime.
from freezegun import freeze_time
class Test(TestCase):
@freeze_time("2017-01-01")
def test_get_tomorrow_4(self):
self.assertEqual("20170102", get_tomorrow())
Le courant est fixé à 2017/1/1 par la description de @freeze_time (" 2017-01-01 ")
.
Ainsi, get_tomorrow ()
retournera toujours " 20170102 "
et réussira à chaque fois que vous exécuterez le test.
Si vous modifiez la date de freeze_time, ce sera pratique car vous pouvez vérifier si le programme fonctionne normalement au fil des ans ou dans l'année de gonflement.
Qu'as-tu pensé. J'ai présenté comment tester une fonction qui dépend de datetime.now ()
de python.
Il est nécessaire de créer un cas de test afin que le test unitaire puisse être exécuté une fois et non terminé, mais puisse être exécuté à tout moment si le CI est tourné.
Je souhaite continuer à apprendre les méthodes de test.
Recommended Posts