pytest 集成 - 如何正确导入
pytest integration - how to properly import
我正在使用 py.test
来测试我的 python 代码。我项目的相关结构是
-myproject
file.py
file2.py
-test/
input.txt
input2.dat
test_part.py
-regress/
file2_old.py
__init__.py
-test/
test_file2_regression.py
test_part.py
导入 file
和 file2
,test_file2_regression.py
导入 file2
和 regress.file2_old
。如果我在控制台中 运行 pytest
,我会收到导入错误,即包不存在。另一方面,运行 python -m pytest
工作得很好,但前提是我 运行 它来自 myproject/
目录。
执行此操作的正确方法是什么,以使其在我的项目中的任何位置工作?我已经尝试修改 PYTHONPATH
但老实说我不知道如何正确地修改它。
更多信息:
我没有任何安装文件,我的 __init__
只是空文件。如果需要操作 PYTHONPATH
,则需要相对于 myproject
进行操作,因为我在多台机器上使用它。我是 运行宁 python 2.7.
我已经退房了:
- Importing correctly with pytest
- Good Integration Practices
但这并没有真正帮助我。
在搜索 "the best way of doing this" 时遇到同样的问题和类似的成功,我总结自己尽可能避免这种情况(通过 运行 实际脚本从顶层开始),但要回答你的问题,我目前的方法(例如从并行文件夹进行单元测试)是
from sys import argv, path
from os.path import dirname, join
path.append(join(dirname(argv[0]), ".."))
这使得解释器也会在上面启动脚本的文件夹中进行搜索。另一种方法(而不是使用 argv
)是使用 introspect
模块来获取文件名。这些对我来说比使用 __file__
更有效,因为后者并不总是被定义。
编辑 29.10.:
argv[0]
的替代方法是使用
from inspect import getsourcefile
from sys import path
from os.path import dirname, join
this_file = getsourcefile(lambda _: None)
path.append(join(dirname(this_file), ".."))
我希望这至少能达到要求的目的,另请参阅 How do I get the path of the current executed file in Python?。
最简单的——如果它适用于你的情况——当然是:
from os.path import dirname, join
path.append(join(dirname(__file__), ".."))
从项目中的任何目录使用 pytest
命令的解决方案是在 test*.py
文件中的导入之前包含:
import os
from sys import path
PATH = os.path.abspath(os.path.dirname(__file__))
path.append(os.path.join(PATH, os.pardir, os.pardir))
正确数量的 os.pardir
用于导航到项目目录,__init__.py
文件允许从那里导入模块。
argv[0]
和 inspect.getsourcefile
都没有提供必要的信息。 argv[0]
包含使用的 py.test
模块的位置和 getsourcefile
方法简单 returns None
.
编辑:从 Python 3.4 开始,我们可以使用现代 pathlib
:
而不是 os.path
from pathlib import Path
from sys import path
PATH = Path(__file__).resolve()
path.append(PATH.parents[2])
我正在使用 py.test
来测试我的 python 代码。我项目的相关结构是
-myproject
file.py
file2.py
-test/
input.txt
input2.dat
test_part.py
-regress/
file2_old.py
__init__.py
-test/
test_file2_regression.py
test_part.py
导入 file
和 file2
,test_file2_regression.py
导入 file2
和 regress.file2_old
。如果我在控制台中 运行 pytest
,我会收到导入错误,即包不存在。另一方面,运行 python -m pytest
工作得很好,但前提是我 运行 它来自 myproject/
目录。
执行此操作的正确方法是什么,以使其在我的项目中的任何位置工作?我已经尝试修改 PYTHONPATH
但老实说我不知道如何正确地修改它。
更多信息:
我没有任何安装文件,我的 __init__
只是空文件。如果需要操作 PYTHONPATH
,则需要相对于 myproject
进行操作,因为我在多台机器上使用它。我是 运行宁 python 2.7.
我已经退房了:
- Importing correctly with pytest
- Good Integration Practices
但这并没有真正帮助我。
在搜索 "the best way of doing this" 时遇到同样的问题和类似的成功,我总结自己尽可能避免这种情况(通过 运行 实际脚本从顶层开始),但要回答你的问题,我目前的方法(例如从并行文件夹进行单元测试)是
from sys import argv, path
from os.path import dirname, join
path.append(join(dirname(argv[0]), ".."))
这使得解释器也会在上面启动脚本的文件夹中进行搜索。另一种方法(而不是使用 argv
)是使用 introspect
模块来获取文件名。这些对我来说比使用 __file__
更有效,因为后者并不总是被定义。
编辑 29.10.:
argv[0]
的替代方法是使用
from inspect import getsourcefile
from sys import path
from os.path import dirname, join
this_file = getsourcefile(lambda _: None)
path.append(join(dirname(this_file), ".."))
我希望这至少能达到要求的目的,另请参阅 How do I get the path of the current executed file in Python?。
最简单的——如果它适用于你的情况——当然是:
from os.path import dirname, join
path.append(join(dirname(__file__), ".."))
从项目中的任何目录使用 pytest
命令的解决方案是在 test*.py
文件中的导入之前包含:
import os
from sys import path
PATH = os.path.abspath(os.path.dirname(__file__))
path.append(os.path.join(PATH, os.pardir, os.pardir))
正确数量的 os.pardir
用于导航到项目目录,__init__.py
文件允许从那里导入模块。
argv[0]
和 inspect.getsourcefile
都没有提供必要的信息。 argv[0]
包含使用的 py.test
模块的位置和 getsourcefile
方法简单 returns None
.
编辑:从 Python 3.4 开始,我们可以使用现代 pathlib
:
os.path
from pathlib import Path
from sys import path
PATH = Path(__file__).resolve()
path.append(PATH.parents[2])