Absolute/relative 在 Python 中导入:ModuleNotFoundError 等等
Absolute/relative import in Python: ModuleNotFoundError and more
这是我的项目结构:
- config
- data
- src
- resources
- db
- test
N.B.: 我正在使用 Python 3.9,每个包含 .py 文件的文件夹也有一个 __init__.py
文件
我想要 运行 的所有脚本都位于 /src 文件夹中,它们使用了放置在 /src/resources 文件夹(基本上就像一个库)中的其他脚本的代码。
其中一些脚本还从 /config 文件夹中读取 YAML 文件
这就是问题所在,我找不到从命令行正确 运行 这些脚本的方法,我总是收到如下错误:
Traceback (most recent call last):
File "/usr/local/lib/python3.8/runpy.py", line 185, in _run_module_as_main
mod_name, mod_spec, code = _get_module_details(mod_name, _Error)
File "/usr/local/lib/python3.8/runpy.py", line 111, in _get_module_details
__import__(pkg_name)
File "/home/pi/crypto/src/ethMessage.py", line 4, in <module>
import update_db
File "/home/pi/crypto/src/update_db.py", line 1, in <module>
from db.mysql_main import insertValueAndFee
File "/home/pi/crypto/src/db/mysql_main.py", line 6, in <module>
from src.resources.parser import read_yaml
ModuleNotFoundError: No module named 'src'
我尝试了相对导入和绝对导入,现在我正在使用绝对导入(例如 from src.resources.parser import read_yaml)
从命令行 运行 脚本的正确方法是什么?
编辑:
按照你的建议,我添加了
sys.path.append( os.path.abspath(os.path.dirname(__file__)+'/..') )
所有主要脚本,我仍然收到类似的错误:
Traceback (most recent call last):
File "src/ethMessage.py", line 6, in <module>
import update_db
File "/home/pi/crypto/src/update_db.py", line 1, in <module>
from db.mysql_main import insertValueAndFee
File "/home/pi/crypto/src/db/mysql_main.py", line 6, in <module>
from src.resources.parser import read_yaml
ModuleNotFoundError: No module named 'src'
澄清一下,我运行正在从全局文件夹中创建我的脚本,在我的例子中,它被命名为“crypto”。
我也愿意用不会产生问题的方式更改项目结构。
如果您想通过根名称引用所有这些包,那么您只需将该文件夹添加到 Python 路径即可。所以,对于 src 中的主程序脚本,只需添加如下内容:
import os
import sys
sys.path.append( os.path.abspath(os.path.dirname(__file__)+'/..') )
现在,无论您 运行 它来自何处,脚本的父目录都将位于路径中。现在你可以说
from src.resources.parser import read_yaml
如果有人仍在寻找解决方案,我强烈建议不要理会 Python 的导入:它们可能是整个语言中最糟糕的部分。
相反,如果您想将某些文件用作库,则应使用 setuptools 从这些文件创建包。
然后,您可以在本地安装它,也可以在 PyPi 上发布它。
通过这种方式,您可以像导入另一个第三方模块(例如请求、selenium 等)一样在脚本中导入您的库,一切都会正常进行,而不是让您头疼,因为文件是在一个目录而不是另一个目录中。
这是我的项目结构:
- config
- data
- src
- resources
- db
- test
N.B.: 我正在使用 Python 3.9,每个包含 .py 文件的文件夹也有一个 __init__.py
文件
我想要 运行 的所有脚本都位于 /src 文件夹中,它们使用了放置在 /src/resources 文件夹(基本上就像一个库)中的其他脚本的代码。 其中一些脚本还从 /config 文件夹中读取 YAML 文件
这就是问题所在,我找不到从命令行正确 运行 这些脚本的方法,我总是收到如下错误:
Traceback (most recent call last):
File "/usr/local/lib/python3.8/runpy.py", line 185, in _run_module_as_main
mod_name, mod_spec, code = _get_module_details(mod_name, _Error)
File "/usr/local/lib/python3.8/runpy.py", line 111, in _get_module_details
__import__(pkg_name)
File "/home/pi/crypto/src/ethMessage.py", line 4, in <module>
import update_db
File "/home/pi/crypto/src/update_db.py", line 1, in <module>
from db.mysql_main import insertValueAndFee
File "/home/pi/crypto/src/db/mysql_main.py", line 6, in <module>
from src.resources.parser import read_yaml
ModuleNotFoundError: No module named 'src'
我尝试了相对导入和绝对导入,现在我正在使用绝对导入(例如 from src.resources.parser import read_yaml)
从命令行 运行 脚本的正确方法是什么?
编辑:
按照你的建议,我添加了
sys.path.append( os.path.abspath(os.path.dirname(__file__)+'/..') )
所有主要脚本,我仍然收到类似的错误:
Traceback (most recent call last):
File "src/ethMessage.py", line 6, in <module>
import update_db
File "/home/pi/crypto/src/update_db.py", line 1, in <module>
from db.mysql_main import insertValueAndFee
File "/home/pi/crypto/src/db/mysql_main.py", line 6, in <module>
from src.resources.parser import read_yaml
ModuleNotFoundError: No module named 'src'
澄清一下,我运行正在从全局文件夹中创建我的脚本,在我的例子中,它被命名为“crypto”。 我也愿意用不会产生问题的方式更改项目结构。
如果您想通过根名称引用所有这些包,那么您只需将该文件夹添加到 Python 路径即可。所以,对于 src 中的主程序脚本,只需添加如下内容:
import os
import sys
sys.path.append( os.path.abspath(os.path.dirname(__file__)+'/..') )
现在,无论您 运行 它来自何处,脚本的父目录都将位于路径中。现在你可以说
from src.resources.parser import read_yaml
如果有人仍在寻找解决方案,我强烈建议不要理会 Python 的导入:它们可能是整个语言中最糟糕的部分。
相反,如果您想将某些文件用作库,则应使用 setuptools 从这些文件创建包。
然后,您可以在本地安装它,也可以在 PyPi 上发布它。
通过这种方式,您可以像导入另一个第三方模块(例如请求、selenium 等)一样在脚本中导入您的库,一切都会正常进行,而不是让您头疼,因为文件是在一个目录而不是另一个目录中。