Тесты записывают отчёты во временные файлы: какую гарантию даёт фикстура pytest tmp_path каждому тесту?
Фикстура tmp_path предоставляет каждому запуску теста отдельный временный каталог в виде объекта pathlib.Path. Поэтому файлы одного теста не должны пересекаться с файлами другого теста при обычном последовательном запуске.
Это изоляция пространства имён, а не полная изоляция процессов или операционной системы. Каталог создаётся pytest, а его жизненный цикл и правила хранения временных данных контролируются самим pytest.
Тестам часто требуется записывать конфигурации, загруженные документы, кэш или промежуточные результаты. Ручное создание каталогов приводит к дублированию кода, конфликтам имён и оставшимся после тестов файлам.
Фикстура tmp_path переносит управление временным каталогом в pytest: тест получает уже подготовленное уникальное место и не должен самостоятельно выбирать имя или решать вопрос базового каталога.
Если несколько тестов используют один каталог, они могут случайно читать файлы, созданные предыдущим тестом. Такой тест иногда проходит локально, но падает при другом порядке запуска, повторном прогоне или параллельном выполнении.
Неверно считать, что сам факт использования tmp_path делает тест полностью независимым. Тест всё ещё может изменять глобальное состояние, обращаться к общему внешнему каталогу или явно использовать один и тот же путь вместо выданного pytest каталога.
tmp_path имеет область действия на функцию: для каждого тестового вызова pytest предоставляет отдельный каталог. При параметризации это означает отдельный временный каталог для каждого параметризованного экземпляра теста.
Объект имеет тип pathlib.Path, поэтому операции выполняются через стандартные методы работы с путями. Например:
Каталог теста находится внутри временного дерева, организованного pytest. pytest сохраняет ограниченное число таких деревьев запусков для диагностики; это не следует путать с гарантией немедленного удаления каждого файла после теста.
Если несколько тестов должны использовать один общий временный ресурс, применяют tmp_path_factory с подходящей фикстурой. Это уменьшает стоимость подготовки, но ослабляет изоляцию: изменение общего каталога одним тестом может повлиять на другой.
Для уникальных временных файлов вне pytest-каталога подходят средства стандартной библиотеки, например tempfile. Однако смешивание подходов без необходимости усложняет очистку и анализ места, где были созданы артефакты.
Интеграционные тесты генерируют большие JSON-отчёты. Изначально все тесты писали их в каталог test-output с фиксированными именами. При параллельном запуске отчёты перезаписывались, а результаты зависели от порядка выполнения.
Рассматривались два варианта. Общий каталог с уникальными именами потребовал бы самостоятельно синхронизировать генерацию имён и очистку. Создание каталога через стандартный tempfile решило бы конфликт, но добавило бы служебный код в каждый тест.
Выбрали tmp_path: каждый тест сохранял отчёт в свой каталог, а путь к нему передавался в тестируемый код. В результате исчезли конфликты имён, а pytest сохранил возможность оставить временные данные последних запусков для расследования падений.
Да. Каждый параметризованный экземпляр считается отдельным выполнением теста и получает собственный tmp_path. Поэтому данные одного набора параметров не должны использоваться другим через эту фикстуру.
Используют tmp_path_factory, обычно через отдельную фикстуру с более широкой областью действия. Это оправдано для дорогого общего ресурса, например заранее распакованного набора данных, но тесты должны явно учитывать общий доступ и не изменять исходные файлы без копирования.
Он снижает риск конфликтов файлов, поскольку тесты получают разные каталоги. Но полной гарантии нет: конфликты возможны при обращении к общим внешним путям, сетевым ресурсам, переменным окружения или при использовании одного общего ресурса через tmp_path_factory. Изоляцию файловой области нужно сочетать с контролем остальных видов состояния.