Pytest 项目运行速度非常慢

Sin*_*yen 8 python pytest python-3.x

我的 pytest 设置运行得很慢,尤其是在收集阶段。

所以我为我的 Django 项目建立了一个 pytest 设置,每个 Django 应用程序的测试文件都位于它自己的文件夹中,即树看起来如下

root
|
+--a
|  |
|  +--tests
|       |
|       +--conftest.py
|       +--testAa.py
|       +--testBa.py
+--b
|  |
|  +--tests
|       |
|       +--conftest.py
|       +--testAb.py
|       +--testBb.py
...
pytest.ini
Run Code Online (Sandbox Code Playgroud)

pytest.ini 文件指定在何处查找测试并具有以下内容

[pytest]
DJANGO_SETTINGS_MODULE = project.project.settings.test
python_files = tests.py test_*.py *_tests.py
addopts = --reuse-db
Run Code Online (Sandbox Code Playgroud)

对于tests文件夹中的每个应用程序,我都有一个名为contest.py. 此文件创建一组在测试文件中多次使用的对象。例如,如果类的对象A被多次使用,则竞赛会创建该变量一次,并且测试使用此 conftest 作为输入。每个 conftest 都有装饰器@pytest.fixture(scope="function"),测试有装饰器@pytest.mark.django_db

我不认为加载时间是由 conftests 或上一段中讨论的装饰器引起的,而是由pytest.ini我提供的树结构和文件引起的。对于什么是好的结构,是否有任何规则?正如我所说,收集测试的加载时间非常长。更准确地说,我有大约 80 个测试,收集它们大约需要 40 秒。运行它们都需要额外的 20。

hoe*_*ing 9

或多或少重申我的另一个答案

当您调用 时pytest,它将扫描项目根目录中的每个子目录,寻找测试。这可能会减慢测试收集速度;从扫描中排除不相关的目录可能是明智的。pytest为此提供了两个配置选项:

  1. norecursedirs- 保存将从扫描中排除的目录。当您在寻找“包括所有,排除选定的”模式时使用此选项。默认情况下,norecursedirs设置为'.*', 'build', 'dist', 'CVS', '_darcs', '{arch}', '*.egg',因此请注意,当您覆盖此选项时,默认值将消失,您必须重新添加它们。
  2. testpaths- 保存只应考虑用于扫描的目录,因此这基本上与norecursedirs正在执行的操作相反。查找模式“排除所有,包括所选”时使用此选项。此选项还为测试发现增加了一些较小或更显着的加速,具体取决于您在项目根目录中保留的内容 - 根本不会遍历大多数子目录,并且测试运行会更快开始。

使用方法:要么把这些选项在pytest.ini/ setup.cfg/ tox.ini

[tool:pytest]
testpaths = tests othertests doc
Run Code Online (Sandbox Code Playgroud)

或通过--override-ini命令行传递它们。

pytest -o "testpaths=tests othertests doc" ...
Run Code Online (Sandbox Code Playgroud)


max*_*moo 9

对我来说,问题在于某个特定的conftest.py运行需要很长时间(它为我在这里不需要的不同测试设置了一些巨大的固定装置)。

这很难诊断,因为仅在--collect-only 标记和自定义rootdir设置为测试目录时仍然会发生延迟(conftest 位于很远的不同目录中,但仍以某种方式检测到)。

我的解决方案是运行pytest --noconftest.