SQLAlchemy 字符串关系导致 flake8 和 mypy 投诉“未定义名称”

问题描述 投票:0回答:1
# order.py
class Order(Base):
    __tablename__ = "Order"

    id: Mapped[int] = mapped_column(primary_key=True)
    items: Mapped[List["Item"]] = relationship(back_populates="order")

# item.py
class Item(Base):
    __tablename__ = "Item"

    id: Mapped[int] = mapped_column(primary_key=True, autoincrement=True)
    order_id: Mapped[int] = mapped_column(ForeignKey("Order.id"))
    order: Mapped["Order"] = relationship(back_populates="items")

我正在使用 sqlalchemy 2.0.23,不使用 mypy 或 flake8 的插件。

两个模块都不需要导入另一个,因为我在 Order 类中使用字符串关系,例如“Item”,在 Item 类的关系中使用“Order”。

flake8 由于未定义名称而对两个文件报告 F821 错误。
mypy 在两者上都报告了类似的错误。

我可以配置 flake8 来忽略 F821。我不确定我会如何在 mypy 中做类似的事情。但这些重要的规则不应该被关闭以通过 linter 获取 SQLAlchemy 类。

我想将我的课程保存在单独的文件中。有没有办法正确定义它们,这样像这样的 linter 就不会抱怨?向这两个文件添加导入可以使这些 linter 安静下来,但会导致循环导入问题,因此代码将无法运行。

python sqlalchemy relationship mypy flake8
1个回答
0
投票

mypy
flake8
在这里是正确的,这些警告不应被忽略。要解决循环导入问题,您可以使用“仅类型检查导入”,即包装在
import
块中的
if TYPE_CHECKING
语句(
TYPE_CHECKING
常量在 here 进行了解释)。它可能是这样的:

# order.py
from typing import TYPE_CHECKING

if TYPE_CHECKING:
    from .item import Item


class Order(Base):
    __tablename__ = "Order"

    id: Mapped[int] = mapped_column(primary_key=True)
    items: Mapped[List["Item"]] = relationship(back_populates="order")

# item.py
from typing import TYPE_CHECKING

if TYPE_CHECKING:
    from .order import Order


class Item(Base):
    __tablename__ = "Item"

    id: Mapped[int] = mapped_column(primary_key=True, autoincrement=True)
    order_id: Mapped[int] = mapped_column(ForeignKey("Order.id"))
    order: Mapped["Order"] = relationship(back_populates="items")
© www.soinside.com 2019 - 2024. All rights reserved.