14

如何使用flask sqlalchemy将列定义为正整数?

我希望答案看起来像这样:

class City(db.Model):
    id = db.Column(db.Integer, primary_key=True)
    population = db.Column(db.Integer, positive=True)
    def __init__(self,population):
        self.population = population

但是,此类定义将引发错误 b/c sqlalchemy 不知道“肯定”参数。

如果对象被实例化为人口的负值,我可能会引发异常。但我不知道如何确保更新后人口保持积极状态。

谢谢你的帮助。

4

2 回答 2

29

不幸的是,在 python 方面,sqlalchemy 尽最大努力不碍事;没有“特殊的 sqlalchemy”方式来表示实例属性必须满足某些约束:

>>> class Foo(Base):
...     __tablename__ = 'foo'
...     id = Column(Integer, primary_key=True)
...     bar = Column(Integer)
...
>>> f = Foo()
>>> f.bar = "not a number!"
>>> f.bar
'not a number!'

如果您尝试提交此对象,sqlalchey抱怨,因为它不知道如何将提供的 python 值呈现为列 type 的 SQL Integer

如果这不是您想要的,您只是想确保不良数据不会到达数据库,那么您需要一个Check约束。

class Foo(Base):
    __tablename__ = 'foo'
    id = Column(Integer, primary_key=True)
    bar = Column(Integer)
    __table_args__ = (
        CheckConstraint(bar >= 0, name='check_bar_positive'),
        {})
于 2013-01-09T00:19:11.293 回答
2

我知道这很旧,但就其价值而言,我的方法是使用棉花糖(反序列化和数据验证库)来验证输入数据。

为您的模型创建架构,如下所示:

from marshmallow import validate, fields, Schema

... 

class CitySchema(Schema):
    population = fields.Integer(validate=validate.Range(min=0, max=<your max value>))

然后在适当的时候使用你的模式来序列化/反序列化数据:

... 
city_data = {...} # your city's data (dict)
city_schema = CitySchema()
deserialized_city, validation_errors = city_schema.load(city_data) # validation done at deserialization
... 

使用反序列化库的优点是您可以在一个地方强制执行所有数据完整性规则

于 2018-01-09T19:36:29.870 回答