Любишь кодить - люби и тестировать. Фундаментальность программистского образования в СССР нивелировалась полным отсутствием представления об организации процесса тестирования, и вообще обеспечения качества программного продукта. Ни в курчатнике, где мы делали операционную систему Демос, ни в ИТМиВТ, с которым мы активно сотрудничали и где разрабатывали штатные ОС и компиляторы для БЭСМ и Эльбрус, не было соответствующей практики наработки тестов и организации регулярного тестирования. А жаль.
С опытом я прихожу к мысли, что современные методики типа
TDD представляют основу практики программирования. Впрочем, про TDD я напишу позже, а сейчас я веду к тому, что
pytest представляет собой первейший инструмент всякого Питон-программиста. Мне лично доводится использовать
pytest по работе и я нахожу его весьма полезным.
Pytest представляет собой утилиту, которая вызывается из командной строки и запускает набор тестов Вашей программы. Для этого pytest сканирует присутствующие папки и файлы в них, находит файлы с именами
test_*.py, а в них определения процедур с именами вида
test_xxx(), и вызывает эти процедуры. На экран выдаётся информация о пройденных тестах. По умолчанию печатается имя файла и дальше точка для каждого успешного теста или F для неуспешного. Скажем, у меня есть файл
test_demo.py и в нём десять тестов. Будет выдано следующее:
$ pytest
======================== test session starts =========================
platform darwin -- Python 3.8.4, pytest-5.4.3, py-1.9.0, pluggy-0.13.1
rootdir: /Users/vak/Project/Github/Pytest-Actions-Demo
collected 10 items
test_demo.py .......... [100%]
========================= 10 passed in 0.03s ========================
Если добавить флаг -v, будут выдаваться имена тестов, по одному в строке:
$ pytest -v
======================== test session starts =========================
platform darwin -- Python 3.8.4, pytest-5.4.3, py-1.9.0, pluggy-0.13.1 -- /usr/local/opt/python@3.8/bin/python3.8
cachedir: .pytest_cache
rootdir: /Users/vak/Project/Github/Pytest-Actions-Demo
collected 10 items
test_demo.py::test_fact_0 PASSED [ 10%]
test_demo.py::test_fact_1 PASSED [ 20%]
test_demo.py::test_fact_2 PASSED [ 30%]
test_demo.py::test_fact_3 PASSED [ 40%]
test_demo.py::test_fact_10 PASSED [ 50%]
test_demo.py::test_fact_20 PASSED [ 60%]
test_demo.py::test_fact_30 PASSED [ 70%]
test_demo.py::test_fact_40 PASSED [ 80%]
test_demo.py::test_fact_50 PASSED [ 90%]
test_demo.py::test_fact_minus1 PASSED [100%]
========================= 10 passed in 0.03s ========================
Процедуры тестов содержат операторы
assert, проверяющие результат выполнения Вашей программы. Если результат совпадает - тест считается успешным:
def test_fact_3():
assert demo.factorial(3) == 6
Если в одном из тестов обнаружена ошибка, она выдаётся в виде:
============================== FAILURES ==============================
____________________________ test_fact_3 _____________________________
def test_fact_3():
> assert demo.factorial(3) == 7
E assert 6 == 7
E +6
E -7
test_demo.py:24: AssertionError
====================== short test summary info =======================
FAILED test_demo.py::test_fact_3 - assert 6 == 7
==================== 1 failed, 9 passed in 0.06s =====================
Да, я не упомянул: устанавливается pytest командой "
pip install pytest". А если добавить к нему ещё и "
pip3 install pytest-xdist", то у
pytest появится флаг "
-nauto", запускающий тесты впараллель на всех доступных процессорах компьютера. Это заметно ускоряет процесс. К примеру у меня на работе в одном из проектов имеется больше 600 тестов, и полный прогон (на одном процессоре) занимает около 15 минут. С флагом же "
-nauto" задействуется 16 процессоров моего MacBook Pro, и тестирование ускоряется до 5 минут.
Это базовый минимум. Но в
pytest есть куча полезных фич, помогающих в разработке тестов. Рекомендую книжку, где все возможности подробно описаны: "
Python Testing with pytest".

Пример проекта с
pytest смотрите на Гитхабе:
https://github.com/sergev/Pytest-Actions-Demo