【问题标题】:Sql-alchemy Integrity errorSqlalchemy 完整性错误
【发布时间】:2017-05-03 11:16:13
【问题描述】:

我有如下描述的用户模型:-

class User(db.Model, object):
    __tablename__ = "users"
    id = db.Column(db.Integer, primary_key=True)
    username = db.Column(db.String(15), unique=True)
    email = db.Column(db.String(50), unique=True)
    password = db.Column(db.String(80))

    def is_authenticated(self):
        return True

    def is_active(self):
        return True

    def get_id(self):
        return unicode(self.id)

现在我有一个注册表,描述如下:-

class RegisterForm(Form):
    email = StringField('email', validators=[InputRequired(), Email(message='Invalid email'), Length(max=50)])
    username = StringField('username', validators=[InputRequired(), Length(min=4, max=15)])
    password = PasswordField('password', validators=[InputRequired(), Length(min=8, max=80)])

现在的问题,

当我通过网络应用注册/注册时,id 会自动增加并创建一个新用户。所以我创建了 user1,id1 由 sql-alchemy 通过注册表自动分配。

现在我在数据库中使用插入语句插入具有有效 id 的新用户。所以我通过数据库中的insert语句创建了带有id2的user2。

如果我尝试通过 web-app 创建 user3,它会显示 sqlalchemy.exc.IntegrityError IntegrityError:(psycopg2.IntegrityError)重复键值违反唯一约束“users_pkey” 详细信息:键 (id)=(2) 已存在。

现在,如果我再次尝试使用 user3 注册,它会创建一个新用户。

我尝试使用自动加载让烧瓶知道最近的 id,但它不起作用。

【问题讨论】:

  • 您可以将 id 设置为显式递增,如下所示:id = db.Column(db.Integer, primary_key=True, autoincrement=True)
  • 包含 autoincrement=True 时不起作用。如果我在出现错误后重试,它会增加。
  • 添加..., autoincrement=True 后,您是否将更改应用到您的数据库?这不会自动发生,您必须以某种方式迁移现有数据库,即将整数主键列更改为串行。
  • @IljaEverilä 我认为需要使用 sql-migrate 和 alembic 来这样做,或者重新启动烧瓶服务器就可以了,还是应该删除整个表?
  • 我没有使用 sql-migrate 的经验,但是 alembic 非常适合处理项目迁移。如果您刚刚开始并且没有太多数据,那么删除并重新创建是一种简单的方法。

标签: python sqlalchemy


【解决方案1】:

一个技巧是从 id 列中查询最大 id 并将其递增 1 并将其分配给新用户以防止主键冲突。

max_id = session.query(User).order_by(User.id.desc()).first()
new_user = User(id=max_id+1, email=form.email.data, username=form.username.data, password=hashed_password)
db.session.add(new_user)
db.session.commit()

【讨论】:

    【解决方案2】:

    只需使用序列来自动增加您的 id。

    from sqlalchemy import Integer, Sequence
    
    id = Column(Integer, Sequence('id_seq'), primary_key=True)
    

    【讨论】:

    • 您是否重新创建了架构?确保已创建序列。
    猜你喜欢
    • 2011-08-10
    • 1970-01-01
    • 2015-05-16
    • 2013-07-12
    • 2015-06-09
    • 2012-07-04
    • 2018-06-08
    • 2016-09-26
    • 1970-01-01
    相关资源
    最近更新 更多