Expert Python
- Comment créer une page d'accueil dynamique WordPress • WPShout
- Travailler avec les rôles et capacités des utilisateurs WordPress • WPShout
- Travailler avec les rôles et capacités des utilisateurs WordPress • WPShout
- 35 meilleurs plugins WordPress Widget pour (presque) tout
- Episode # 181 30 projets Python étonnants
Le framework de test unittest est le framework de style xUnit de python.
C'est un module standard que vous avez déjà si vous avez la version 2.1 ou supérieure de Python.
Dans cet article, je couvrirai les bases de la création et de l'exécution d'un test simple en utilisant unittest.
Ensuite, je montrerai comment je l’utilise pour tester markdown.py.
Vue d'ensemble de unittest
Le module unittest s'appelait auparavant PyUnit, en raison de son héritage en tant que framework de style xUnit.
Il fonctionne de la même manière que les autres styles de xUnit, et si vous êtes familiarisé avec les tests unitaires dans d’autres langues, ce cadre (ou ses versions dérivées) peut être le plus confortable pour vous.
Le flux de travail standard est:
1. Vous définissez votre propre classe dérivée de unittest.TestCase.
2. Ensuite, remplissez-le avec les fonctions qui commencent par «test_».
3. Vous exécutez les tests en plaçant unittest.main ()
dans votre dossier, généralement en bas.
L'un des nombreux avantages de Unittest, que vous utiliserez lorsque vos tests deviendront plus volumineux que les exemples de jouets illustrés sur ce blog, est l'utilisation des fonctions 'setUp' et 'tearDown' pour que votre système soit prêt pour les tests. .
Comme dans l'introduction du doctest, je vais d'abord passer en revue un exemple simple, puis montrer comment j'utilise unittest pour tester markdown.py.
exemple unittest
En utilisant le même module inutile_math.py que j'ai écrit dans le
doctest intro, voici un exemple de test
code pour tester ma fonction "multiplier".
test_um_unittest.py:
importer unittest
de nécessité_math importer multiplier
Classe TestUM (unittest.TestCase):
def setUp (auto):
passer
def test_numbers_3_4 (auto):
self.assertEqual (multiplier (3,4), 12)
def test_strings_a_3 (auto):
self.assertEqual (multiplier ('a', 3), 'aaa')
si __name__ == '__main__':
unittest.main ()
importation Test de l'unité de inut_math importation multiplier classe TestUM(Test de l'unité.Cas de test): def installer(soi): passer def test_numbers_3_4(soi): soi.affirmerEqual( multiplier(3,4), 12) def test_strings_a_3(soi): soi.affirmerEqual( multiplier('une',3), 'aaa') si __prénom__ == '__principale__': Test de l'unité.principale() |
Dans cet exemple, j’ai utilisé assertEqual ()
. Le cadre unittest a tout un tas de assertBlah ()
fonctions de style comme assertEqual ()
. Une fois que vous avez une référence raisonnable pour toutes les fonctions d’assertion marquées, le travail avec unnittest est assez puissant et facile.
Outre les tests que vous écrivez, vous pouvez réaliser la plupart de vos tâches avec les méthodes de test telles que setUp, tearDown, setUpClass, tearDownClass, etc.
Exécuter unittests
Au bas du fichier de test, nous avons ce code:
si __name__ == '__main__':
unittest.main ()
si __prénom__ == '__principale__': Test de l'unité.principale() |
Cela nous permet d'exécuter tout le code de test simplement en exécutant le fichier.
L’exécuter avec aucune option est le plus concis, et exécuter avec un «-v» est plus détaillé, montrant quels tests
a couru.
> python test_um_unittest.py
..
————————————————– ——————–
A couru 2 tests en 0.000s
D'accord
> python test_um_unittest.py -v
test_numbers_3_4 (__main __. TestUM) … ok
test_strings_a_3 (__main __. TestUM) … ok
————————————————– ——————–
A couru 2 tests en 0.000s
D'accord
> python test_um_unittest.py .. ––––––––––––––––––––––––––––––––––– Couru 2 tests dans 0.000s D'accord > python test_um_unittest.py –v test_numbers_3_4 (__principale__.TestUM) ... D'accord test_strings_a_3 (__principale__.TestUM) ... D'accord ––––––––––––––––––––––––––––––––––– Couru 2 tests dans 0.000s D'accord |
Test de découverte
Disons que vous avez un tas de fichiers de test. Il serait ennuyeux de devoir exécuter chaque fichier de test séparément. C’est là que la découverte de test est utile.
Dans notre cas, tout mon code de test (un fichier pour le moment) est en ‘exemple_simple’.
Pour exécuter tous les unittests, utilisez python -m unittest découvrir simple_example
, avec ou sans le «-v», comme ceci:
> python -m unittest discover simple_example
..
————————————————– ——————–
A couru 2 tests en 0.000s
D'accord
> python -m unittest discover -v simple_exemple
test_numbers_3_4 (test_um_unittest.TestUM) … ok
test_strings_a_3 (test_um_unittest.TestUM) … ok
————————————————– ——————–
A couru 2 tests en 0.000s
D'accord
> python –m Test de l'unité découvrir simple_Exemple .. ––––––––––––––––––––––––––––––––––– Couru 2 tests dans 0.000s D'accord > python –m Test de l'unité découvrir –v exemple simple test_numbers_3_4 (test_um_unittest.TestUM) ... D'accord test_strings_a_3 (test_um_unittest.TestUM) ... D'accord ––––––––––––––––––––––––––––––––––– Couru 2 tests dans 0.000s D'accord |
unittest exemple avec markdown.py
Maintenant, je vais lancer un peu plus mon projet markdown.py.
Cela va être assez simple, car les tests sont assez similaires aux versions doctest, juste formatés avec tous les éléments les plus légers, d’autant plus que je n’ai pas besoin d’utiliser des appareils startUp ou tearDown.
test_markdown_unittest.py:
importer unittest
depuis markdown_adapter import run_markdown
classe TestMarkdownPy (unittest.TestCase):
def setUp (auto):
passer
def test_non_marked_lines (auto):
'' '
Les lignes non marquées ne doivent avoir que des balises 'p' autour de toutes les entrées
'' '
self.assertEqual (
run_markdown ('cette ligne n'a pas de traitement spécial'),
'cette ligne n'a pas de traitement spécial
')
def test_em (auto):
'' '
Les lignes entourées d'astérisques doivent être entourées de balises 'em'
'' '
self.assertEqual (
run_markdown ('* cela devrait être encapsulé dans les balises em *'),
'
cela devrait être enveloppé dans les balises em
')
def test_strong (auto):
'' '
Les lignes entourées d'astérisques doubles doivent être entourées de balises "fortes"
'' '
self.assertEqual (
run_markdown ('** ceci devrait être entouré de balises fortes **'),
'
cela devrait être enveloppé dans des étiquettes fortes
')
si __name__ == '__main__':
unittest.main ()
1 2 3 4 5 6 7 8 9 dix 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 |
importation Test de l'unité de markdown_adapter importation run_markdown classe TestMarkdownPy(Test de l'unité.Cas de test): def installer(soi): passer def test_non_marked_lines(soi): ''' Les lignes non marquées ne devraient avoir que 'p'balises autour de toutes les entrées ''' soi.affirmerEqual( run_markdown("cette ligne n'a pas de traitement spécial"), 'cette ligne n'a pas de traitement spécial ') def test_em(soi): ''' Les lignes entourées d'astérisques doivent être enveloppées "em' Mots clés ''' soi.affirmerEqual( run_markdown('* ceci devrait être enveloppé dans les balises em *'), ' cela devrait être enveloppé dans les balises em ') def test_strong(soi): ''' Les lignes entourées d'astérisques doubles doivent être enveloppées "fort' Mots clés ''' soi.affirmerEqual( run_markdown("** ceci devrait être enveloppé dans des étiquettes fortes **"), ' cela devrait être enveloppé dans des étiquettes fortes ') si __prénom__ == '__principale__': Test de l'unité.principale() |
Test de markdown.py
Et maintenant, nous pouvons voir que tout échoue (comme prévu).
> python test_markdown_unittest.py
FFF
=============================================== =====================
FAIL: test_em (__main __. TestMarkdownPy)
————————————————– ——————–
Traceback (dernier appel le plus récent):
Fichier "test_markdown_unittest.py", ligne 29, dans test_em
'cela devrait être enveloppé dans les balises em
')
AssertionError: '* cela devrait être encapsulé dans les balises em *'! = '
cela devrait être enveloppé dans les balises em
'
=============================================== =====================
FAIL: test_non_marked_lines (__main __. TestMarkdownPy)
————————————————– ——————–
Traceback (dernier appel le plus récent):
Fichier "test_markdown_unittest.py", ligne 21, dans test_non_marked_lines
'
cette ligne n'a pas de traitement spécial
')
AssertionError: 'cette ligne n'a pas de traitement spécial'! = '
cette ligne n'a pas de traitement spécial
'
=============================================== =====================
FAIL: test_strong (__main __. TestMarkdownPy)
————————————————– ——————–
Traceback (dernier appel le plus récent):
Fichier "test_markdown_unittest.py", ligne 37, dans test_strong
'
cela devrait être enveloppé dans des étiquettes fortes
')
AssertionError: '** ceci devrait être enveloppé dans des balises fortes **'! = '
cela devrait être enveloppé dans des étiquettes fortes
'
————————————————– ——————–
A couru 3 tests en 0.142s
FAILED (échecs = 3)
1 2 3 4 5 6 7 8 9 dix 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 |
> python test_markdown_unittest.py FFF ====================================================================== ÉCHOUER: test_em (__principale__.TestMarkdownPy) ––––––––––––––––––––––––––––––––––– Traceback (plus récent appel dernier): Fichier "test_markdown_unittest.py", ligne 29, dans tester_em 'cela devrait être enveloppé dans les balises em ') AssertionError: '* ceci devrait être enveloppé dans les balises em *' ! = ' cela devrait être enveloppé dans les balises em ' ====================================================================== ÉCHOUER: test_non_marked_lines (__principale__.TestMarkdownPy) ––––––––––––––––––––––––––––––––––– Traceback (plus récent appel dernier): Fichier "test_markdown_unittest.py", ligne 21, dans test_non_marked_lignes ' cette ligne n'a pas de traitement spécial ') AssertionError: "cette ligne n'a pas de traitement spécial" ! = ' cette ligne n'a pas de traitement spécial ' ====================================================================== ÉCHOUER: test_strong (__principale__.TestMarkdownPy) ––––––––––––––––––––––––––––––––––– Traceback (plus récent appel dernier): Fichier "test_markdown_unittest.py", ligne 37, dans tester_fort ' cela devrait être enveloppé dans des étiquettes fortes ') AssertionError: "** ceci devrait être enveloppé dans des étiquettes fortes **" ! = ' cela devrait être enveloppé dans des étiquettes fortes ' ––––––––––––––––––––––––––––––––––– Couru 3 tests dans 0,142s ÉCHOUÉ (les échecs=3) |
Une chose intéressante à noter par rapport à doctest. Seuls les tests réels sont comptés.
J'ai 3 tests. Et unittest obtient ce droit.
Doctest répertorie 4 tests, l'un d'eux réussissant. Quel est le 4ème? C’est la déclaration d’importation.
Chaque déclaration est comptée dans doctest, donc les comptes sont un peu farfelus, si vous me demandez.
Les comptes sont beaucoup plus significatifs dans unittest.
Plus d'infos unittest
La page python.org sur unittest est une excellente source d’informations sur unittest.
Si vous avez un autre tutoriel ou référence préféré pour unittest, veuillez laisser un commentaire.
De plus, le code présenté ici est disponible sur github.com/varied Thoughts/markdown.py
Prochain
Maintenant que les bases du doctest et du unittest sont terminées, je vais me lancer dans une partie du plaisir en explorant nez, puis py.test.
Ensuite, avant d’aborder d’autres sujets amusants, je devrais probablement demander à mon script markdown.py de faire quelque chose.
Ce faisant, au moins un message sur mon utilisation des expressions régulières en python sera probablement publié.
Retour d'information
J'ai reçu des commentaires par courrier électronique et d'autres moyens.
Merci à tous ceux qui participent à cette discussion.
Si vous ne souhaitez pas laisser de commentaires sur un message, vous pouvez utiliser le formulaire de contact.
Si le formulaire de contact ne fonctionne pas pour vous, ou si vous n'aimez tout simplement pas les formulaires de contact, vous pouvez m'envoyer un email directement.
Le courrier électronique que j'ai configuré pour ce blog est
brian au test python DOT net (pas d'espaces, bien sûr)
J'ai une poignée d'idées pour les prochains articles de blog, je ne peux donc pas promettre de couvrir toutes les suggestions que les gens me font, mais je vais essayer de les intégrer, surtout si je peux apprendre quelque chose dans le processus.
Merci d'avoir lu. Rester en contact!
[ad_2]