使用foreignkey属性的flask sqlalchemy UniqueConstraint

时间:2017-01-17 20:31:52

标签: python flask sqlalchemy flask-sqlalchemy unique-constraint

我正在使用Flask构建的应用程序包含项目和板块的模型,其中Plates将Project作为外键。

每个项目都有一年,以整数给出(2017年为17);每个板都有一个数字和一个名称,由plate.project.year和plate.number构成。例如,今年完成的项目中的板块106将具有名称' 17-0106'。我希望这个名字是独一无二的。

以下是我的模特:

class Project(Model):
    __tablename__   = 'projects'
    id              = Column(Integer, primary_key=True)
    name            = Column(String(64),unique=True)
    year            = Column(Integer,default=datetime.now().year-2000)

class Plate(Model):
    __tablename__   = 'plates'
    id              = Column(Integer, primary_key=True)
    number          = Column(Integer)
    project_id      = Column(Integer, ForeignKey('projects.id'))
    project         = relationship('Project',backref=backref('plates',cascade='all, delete-orphan'))

    @property
    def name(self):
        return str(self.project.year) + '-' + str(self.number).zfill(4)

我的第一个想法是在具有相同project.year属性的板块中使数字唯一,所以我尝试了 __table_args__ = (UniqueConstraint('project.year', 'number', name='_year_number_uc'),),但这需要访问另一个表。

有没有办法在数据库中执行此操作?或者,如果没有这个,__init__方法会检查number / project.year组合或name属性的唯一性?

1 个答案:

答案 0 :(得分:0)

您的问题有多种解决方案。例如,您可以对5*x + r = 2组合进行反规范化,并将其存储为单独的project.year-number字段。然后你可以在上面放一个唯一的钥匙。问题是你将如何保持这个价值。两个明显的选项是触发器(假设您的数据库支持触发器,您可以使用它们)或sqla事件,请参阅http://docs.sqlalchemy.org/en/latest/orm/events.html#

两种解决方案都不会发出额外的SELECT查询。我认为这对你很重要。

您的问题与Can SQLAlchemy events be used to update a denormalized data cache?

有些相似