mypy 无法识别具有hybrid_property的 SQLAlchemy 列



我正在尝试使用SQLAlchemy。为了验证/修改特定的列值(本例中为email), SQLAlchemy官方文档提供了hybrid_property装饰器。

问题是mypy不能正确识别EmailAddress类构造函数,给出:

email_address.py:31: error: Unexpected keyword argument "email" for "EmailAddress"; did you mean "_email"?

我如何告诉我的my识别这些列?

from typing import TYPE_CHECKING
from sqlalchemy import Column, Integer, String
from sqlalchemy.ext.declarative import declarative_base
# I don't even like the following statements just for setter
if TYPE_CHECKING:
hybrid_property = property
else:
from sqlalchemy.ext.hybrid import hybrid_property
Base = declarative_base()

class EmailAddress(Base):
__tablename__ = "email_address"
id = Column(Integer, primary_key=True)
_email = Column("email", String)
@hybrid_property
def email(self):
return self._email
@email.setter
def email(self, email):
self._email = email

EmailAddress(email="foobar@example.com")
# email_address.py:31: error: Unexpected keyword argument "email" for "EmailAddress"; did you mean "_email"?

我使用以下包:

SQLAlchemy==1.4.35
mypy==0.942
mypy-extensions==0.4.3
sqlalchemy2-stubs==0.0.2a22

好了,看来我终于找到解决这个问题的方法了。

这让我想起了这里讨论的数据类/属性装饰器之间的不合作行为。

我最终将EmailAddress类拆分为2:

  1. 在基类上使用@dataclass装饰器来指示构造器选项。
  2. 重写email属性,这样mymyy就不会报错。
from dataclasses import dataclass
from typing import TYPE_CHECKING, Optional
from sqlalchemy import Column, Integer, String, Table
from sqlalchemy.orm import registry
mapper_registry: registry = registry()
# I don't even like the following statements just for setter
if TYPE_CHECKING:
hybrid_property = property
else:
from sqlalchemy.ext.hybrid import hybrid_property

@dataclass
@mapper_registry.mapped
class EmailAddressBase:
__tablename__ = "email address"
id: int = Column(Integer, primary_key=True)
email: Optional[str] = None

class EmailAddress(EmailAddressBase):
_email = Column("email", String)
@hybrid_property
def email(self):
return self._email
@email.setter
def email(self, email):
self._email = email

email = EmailAddress(email="foobar@example.com")
print(email.email)

相关内容

  • 没有找到相关文章

最新更新