如何从另一个目录导入python包?

问题描述 投票:3回答:2

我有一个结构如下的项目:

project
├── api
│   ├── __init__.py
│   └── api.py
├── instance
│   ├── __init__.py
│   └── config.py
├── package
│   ├── __init__.py
│   └── app.py
├── requirements.txt
└── tests
    └── __init__.py

我正在尝试从config.py调用package/app.py文件,如下所示:

# package/app.py
from instance import config

# I've also tried
import instance.config
import ..instance.config
from ..instance import config

但是我总是收到以下错误:

Traceback (most recent call last):
  File "/home/csymvoul/projects/project/package/app.py", line 1, in <module>
    from instance import config
ModuleNotFoundError: No module named 'instance'

修改sys.path不是我想要做的。我知道这个问题已经得到很好的回答,但是给出的答案对我没有用。

EDIT:app.py移动到根文件夹时,它可以正常工作。但是我需要将其放在package文件夹下。

python python-3.x python-module
2个回答
3
投票

您可以将父目录添加到PYTHONPATH,为此,可以在sys.path中列出的“模块搜索路径”中使用OS依赖的路径。因此,您可以轻松添加父目录,如下所示:

import sys
sys.path.insert(0, '..')

from instance import config

请注意,前面的代码使用相对路径,因此您必须在相同位置启动文件,否则可能无法正常工作。要从任何地方启动,可以使用pathlib模块。

from pathlib import Path
import sys
path = str(Path(Path(__file__).parent.absolute()).parent.absolute())
sys.path.insert(0, path)

from instance import config

但是,以前的方法比其他方法更能破解,为使事情正确,首先需要根据这篇非常详细的博客文章python packaging重塑项目结构,并执行以下操作:

  • 安装软件包:

    • 在文件夹的根目录中添加一个setup.py文件
    • 也许创建虚拟环境(可选,但推荐)
    • 使用pip install -e .(带点)命令
  • 然后只需使用from instance import config

  • 导入您的软件包

1
投票

在Python 3.3及更高版本中,您无需在子目录中就需要导入__init__.py文件。如here所述,拥有它们实际上可能会引起误解,因为这会导致在每个包含初始化文件的文件夹中创建程序包名称空间。

通过删除所有这些__init__.py文件,您可以在运行package时将其导入名称空间app.py(包括子目录)中,但这仍然不是我们想要的。

Python解释器仍然不知道如何到达您的instance名称空间。为此,您可以使用PYTHONPATH环境变量,包括config.py父级的路径。您可以按照@RMPR答案sys.path中的建议进行操作,也可以直接设置环境变量,例如:

PYTHONPATH=/home/csymvoul/projects/project python3 /home/csymvoul/projects/project/package/app.py

然后导入依赖项,例如from instance import config

© www.soinside.com 2019 - 2024. All rights reserved.