小编典典

将pytest与src层一起使用

python

pytest建议添加一个附加目录来分隔项目中的源代码:

my_package
├── src  # <-- no __init__.py on this layer
│   └── my_package
│       ├── __init__.py
│       └── util_module
│           ├── __init__.py
│           └── utils.py
└── tests
    ├── __init__.py
    └── test_util_module
        ├── __init__.py
        └── test_utils.py

可悲的是,他们在这种情况下对测试代码中的导入应该如何工作一无所获[1],在这个幼稚的示例[2]中,对于我的IDE来说是很好的,但pytest导致以下错误:

my_package $ pytest

====================== test session starts ======================
platform linux -- Python 3.6.4, pytest-3.5.1, py-1.5.3, pluggy-0.6.0
rootdir: /home/user/workspace/my_package, inifile:
collected 0 items / 1 errors

============================ ERRORS =============================
___ ERROR collecting tests/test_util_module/test_utils.py ___
ImportError while importing test module '/home/user/workspace/my_package/tests/test_util_module/test_utils.py'.
Hint: make sure your test modules/packages have valid Python names.
Traceback:
tests/test_util_module/test_utils.py:1: in <module>
    from test.test_module.some_file import starify
E   ModuleNotFoundError: No module named 'my_package.util_module'
!!!! Interrupted: 1 errors during collection !!!!!

我可以通过将测试的导入更改为来解决此问题from src.my_package.util_module.utils import starify,但随后我的IDE投诉该src部分多余,因此我想将其保留。


[1]
:情况不再如此。从3.7.3版本开始,pytest建议在@hoefling的答案的最佳实践的顶部也提供可编辑的安装。

[2] :设置为virtualenv env -p python3.6; source env/bin/activate; pip install pytest


阅读 300

收藏
2020-12-20

共1个答案

小编典典

调整PYTHONPATH(如注释中所建议)是解决导入问题的一种可能性。另一个方法是conftest.pysrc目录中添加一个空文件:

$ touch src/conftest.py

并且pytest将添加srcsys.path。这是诱骗pytest向中添加代码库的简单方法sys.path

但是,src当您打算构建发行版时,通常会选择布局,例如,提供setup.py(在这种情况下)显式指定根软件包目录:

from setuptools import find_packages, setup


setup(
    ...
    package_dir={'': 'src'},
    packages=find_packages(where='src'),
    ...
)

并在仍在开发时以开发模式(通过python setup.py developpip install --editable .)安装该软件包。这样,您的软件包my_package就可以正确地集成到Python的站点软件包结构中,而无需费心了PYTHONPATH

2020-12-20