首页 > 解决方案 > 动态改变python导入优先级

问题描述

我有一个看起来像这样的文件树:

my_repo/
|-- main/
|   |-- my_script.py
|   |-- __init__.py
|-- common/
|   |-- utils.py
|   |-- __init__.py
|-- config/
|   |-- config.py
|   |-- __init__.py

我已经安装了一个带有文件树的外部包:

some_package
|-- setup.py
|-- config.py
...

安装包后,默认运行import config会从some_package.

my_script.py需要导入common/utils.py运行以下内容:

from config.config import SOME_VALUE

无论我如何尝试重新排列导入路径,我仍然会收到错误消息:

ModuleNotFoundError: No module named 'config.config'; 'config' is not a package

上面的错误显然意味着我们能够common在路径中找到包,但config仍然是从中导入的。some_package 这是我尝试导入common/utils.pymy_script.py,都产生了相同的结果:

sys.path.append('..'); from common import utils
sys.path.append('..'); from common import utils
sys.path.insert(0, '/home/myuser/my_repo'); from common import utils
sys.path.insert(0, '..'); from common import utils
sys.__plen = len(sys.path); sys.path.append('..'); new=sys.path[sys.__plen:]; del sys.path[sys.__plen:]; p=getattr(sys,'__egginsert',0); sys.path[p:p]=new; sys.__egginsert = p+len(new); from common import utils

最后一个想法是取自这里

有人对如何优先考虑我的配置包而不是外部包中的配置包有任何新的想法吗?

我的 python 版本是 3.9.7。谢谢

标签: python

解决方案


在运行您的程序之前添加path-to-project-root/my_repo到您的PYTHONPATH 。从那里,当您要求 Python 导入某些内容时,它会在my_repo目录中找到它(也因为它们每个都包含一个__init__.py,请参阅这篇文章)。
拥有正确的 PYTHONPATH 是一个简单的解决方案,几乎适用于每个项目。

您还可以sys.path在程序启动时编辑列表,但请注意,当append('..')它相对于您的当前目录os.curdir时,这可能是您想要的,也可能不是您想要的。它会根据您执行程序的方式而变化。

sys.path您可以通过打印和os.path.abspath(os.curdir)在程序启动时检查您实际在做什么。


推荐阅读