#python #pytest
#python #pytest
Вопрос:
Вот мой макет каталога тестов API:
api_tests
├── conftest.py
└── query
└── me_test.py
Содержимое conftest.py:
print("CONFTEST LOADED")
Содержимое me_test.py:
"""Tests the "me" query"""
def test_me():
assert True
Если я просто запускаю pytest
, все работает:
================================================= test session starts =================================================
platform linux -- Python 3.8.5, pytest-6.1.0, py-1.9.0, pluggy-0.13.1
rootdir: /home/hubro/myproject, configfile: pytest.ini
collecting ... CONFTEST LOADED
collected 3 items
api_tests/query/me_test.py . [ 33%]
lib/myproject/utils_test.py . [ 66%]
lib/myproject/schema/types/scalars_test.py .
Выводится сообщение «CONFTEST LOADED». Отлично! Однако этот тестовый запуск также собрал все мои модульные тесты, которые мне не нужны. Я хочу разделить свои тестовые прогоны на модульные тесты и тесты API, я не хочу запускать их все за один раз.
Однако, если я просто запускаю pytest api_tests/
:
================================================= test session starts =================================================
platform linux -- Python 3.8.5, pytest-6.1.0, py-1.9.0, pluggy-0.13.1
rootdir: /home/hubro/myproject, configfile: pytest.ini
collected 1 item
api_tests/query/me_test.py . [100%]
================================================== 1 passed in 0.00s ==================================================
Теперь выполняются правильные тесты, но conftest.py файл не был загружен… Как так получилось?
Я использую Pytest 6.1.0 на Python 3.8.
РЕДАКТИРОВАТЬ: Хорошо, я нашел приемлемое решение. Я могу переопределить параметры INI-файла через командную строку с -o
помощью опции. Это работает:
poetry run pytest -o "testpaths=api_tests"
Тем не менее, я бы очень хотел получить ответ на исходный вопрос, поэтому я не собираюсь его удалять.
Комментарии:
1. Локальный
conftest
плагин будет загружен так или иначе. Разница только в коллекции, поэтому печать будет проглочена при втором вызове.2. @hoefling О черт, ты прав… 🤦 Продолжайте и напишите это в ответе, и я отмечу его как правильный…
3. Не волнуйтесь,
pytest
поддержка вложенных тестов довольно сложна и имеет множество нежелательных побочных эффектов, это один из них.
Ответ №1:
conftest
Плагин будет зарегистрирован в обоих вызовах, единственное отличие заключается в стадии регистрации. Если вы сомневаетесь, добавьте --traceconfig
аргумент в список зарегистрированных плагинов в порядке их регистрации:
$ pytest --traceconfig
PLUGIN registered: <_pytest.config.PytestPluginManager object at 0x7f23033ff100>
PLUGIN registered: <_pytest.config.Config object at 0x7f2302d184c0>
...
=================================== test session starts ===================================
...
PLUGIN registered: <module 'conftest' from 'path/to/conftest.py'>
...
При первом вызове файл conftest.py
не будет найден сразу, поскольку он находится по корневому пути теста, поэтому он будет загружен во время pytest
обнаружения тестов. Во втором вызове conftest.py
находится в корне теста, поэтому он будет загружен еще до начала тестового сеанса (после загрузки плагинов, переданных через -p
arg и зарегистрированных через setuptools
entrypoint). Запуск pytest -s
(с отключенным захватом выходных данных) должен показать пользовательскую печать, расположенную над ==== test session starts ====
строкой.
Если вы хотите, чтобы print был идентичным между двумя вызовами, поместите его в подходящий хук. Например, чтобы всегда печатать CONFTEST loaded
после завершения сбора тестов, используйте:
# api_tests/conftest.py
def pytest_collectreport(report):
print("CONFTEST loaded")
Для пользовательского размещения выходных данных доступны и другие варианты; лучше всего проверить список доступных перехватов в pytest
разделе Ссылки на перехваты.