蒸馏器。 env.py 中的 ModuleNotFoundError
Alembic. ModuleNotFoundError in env.py
我有 foloving 项目结构
--some db:
--some db:
--alchemy:
-- __init__.py
--alembic:
-- versions
-- env.py
-- README.py
-- script.py
--migrations:
-- __init__.py
--models:
-- model_1
-- model_2
-- __init__.py
我尝试通过 alembic 自动生成迁移。
我在模型文件夹__init__.py
中有Base
import sqlalchemy as sa
from sqlalchemy.orm import relationship
from sqlalchemy.ext.declarative import declarative_base, declared_attr
metadata = sa.MetaData()
Base = declarative_base(metadata=metadata)
并导入这是 env.py
from logging.config import fileConfig
from alembic import context
from sqlalchemy import engine_from_config
from sqlalchemy import pool
from models import Base
config = context.config
fileConfig(config.config_file_name)
target_metadata = Base.metadata
因此,当我从 alembic 目录中的 env.py 中的模型导入 Base 并尝试生成自动迁移时,我遇到了一些错误,例如
ModuleNotFoundError: No module named 'models'
我该如何解决这个错误?
问题是执行env.py
时,models
不在你的PYTHONPATH
中,所以无法导入。
根据您概述的项目结构,可能有点难以解决;最简单的解决方案可能是像这样在 env.py
中修改 PYTHONPATH
:
import sys
sys.path = ['', '..'] + sys.path[1:]
from models import Base
这会将 alembic/
的父目录添加到您的 PYTHONPATH
以便它可以找到 models
模块。
或者,将包含模块的目录添加到 shell 中的 PYTHONPATH
环境变量中:
$ export PYTHONPATH='/path/to/some db/some db':$PYTHONPATH
此解决方案有点脆弱,因为您必须记住每次会话都执行此操作,并且对于您打算 运行 Alembic on 的每台机器,它都会有所不同。
当我 运行 进入这个问题时,SQLAlchemy 开发人员 suggested that if I was using pip
and virtual environments, I could install my project in editable mode so that it's in the system PYTHONPATH
and Alembic would be able to find it from anywhere. More details are available in the Python packaging guide。为此,您的项目需要一个 setup.py
,并且您可能想要更改项目结构,以便有一个包含 models
和 alchemy
之类的顶级模块。例如:
myproj/
setup.py
alembic/
env.py
migrations/
myapp/
__init__.py
alchemy/
__init__.py
models/
__init__.py
如果设置正确,您可以
$ pip install -e .
从 myproj/
目录中。然后在 env.py
中,您将像这样导入 Base
:
from myapp.models import Base
从 Python 中的文件加载模块时,__file__
设置为其路径。然后,您可以将其与其他函数结合使用来查找文件所在的目录。
在 alembic/env.py 文件中添加以下行以解决 ModuleNotFoundError
BASE_DIR = os.path.dirname(os.path.dirname(os.path.abspath(__file__)))
sys.path.append(BASE_DIR)
现在有一个漂亮的方法:https://github.com/sqlalchemy/alembic/commit/d6b0c1af3df98b50c6ec52781aa411592c4e0c32
”...默认的“alembic.ini”文件包含指令prepend_sys_path = .
,因此本地路径也在sys.path
.
中
我为 Linux 找到了以下解决方案,我觉得这很简单。
运行 命令为:
PYTHONPATH={your python path} {your alembic cmd}
我有 foloving 项目结构
--some db:
--some db:
--alchemy:
-- __init__.py
--alembic:
-- versions
-- env.py
-- README.py
-- script.py
--migrations:
-- __init__.py
--models:
-- model_1
-- model_2
-- __init__.py
我尝试通过 alembic 自动生成迁移。
我在模型文件夹__init__.py
中有Base
import sqlalchemy as sa
from sqlalchemy.orm import relationship
from sqlalchemy.ext.declarative import declarative_base, declared_attr
metadata = sa.MetaData()
Base = declarative_base(metadata=metadata)
并导入这是 env.py
from logging.config import fileConfig
from alembic import context
from sqlalchemy import engine_from_config
from sqlalchemy import pool
from models import Base
config = context.config
fileConfig(config.config_file_name)
target_metadata = Base.metadata
因此,当我从 alembic 目录中的 env.py 中的模型导入 Base 并尝试生成自动迁移时,我遇到了一些错误,例如
ModuleNotFoundError: No module named 'models'
我该如何解决这个错误?
问题是执行env.py
时,models
不在你的PYTHONPATH
中,所以无法导入。
根据您概述的项目结构,可能有点难以解决;最简单的解决方案可能是像这样在 env.py
中修改 PYTHONPATH
:
import sys
sys.path = ['', '..'] + sys.path[1:]
from models import Base
这会将 alembic/
的父目录添加到您的 PYTHONPATH
以便它可以找到 models
模块。
或者,将包含模块的目录添加到 shell 中的 PYTHONPATH
环境变量中:
$ export PYTHONPATH='/path/to/some db/some db':$PYTHONPATH
此解决方案有点脆弱,因为您必须记住每次会话都执行此操作,并且对于您打算 运行 Alembic on 的每台机器,它都会有所不同。
当我 运行 进入这个问题时,SQLAlchemy 开发人员 suggested that if I was using pip
and virtual environments, I could install my project in editable mode so that it's in the system PYTHONPATH
and Alembic would be able to find it from anywhere. More details are available in the Python packaging guide。为此,您的项目需要一个 setup.py
,并且您可能想要更改项目结构,以便有一个包含 models
和 alchemy
之类的顶级模块。例如:
myproj/
setup.py
alembic/
env.py
migrations/
myapp/
__init__.py
alchemy/
__init__.py
models/
__init__.py
如果设置正确,您可以
$ pip install -e .
从 myproj/
目录中。然后在 env.py
中,您将像这样导入 Base
:
from myapp.models import Base
从 Python 中的文件加载模块时,__file__
设置为其路径。然后,您可以将其与其他函数结合使用来查找文件所在的目录。
在 alembic/env.py 文件中添加以下行以解决 ModuleNotFoundError
BASE_DIR = os.path.dirname(os.path.dirname(os.path.abspath(__file__)))
sys.path.append(BASE_DIR)
现在有一个漂亮的方法:https://github.com/sqlalchemy/alembic/commit/d6b0c1af3df98b50c6ec52781aa411592c4e0c32
”...默认的“alembic.ini”文件包含指令prepend_sys_path = .
,因此本地路径也在sys.path
.
我为 Linux 找到了以下解决方案,我觉得这很简单。 运行 命令为:
PYTHONPATH={your python path} {your alembic cmd}