我正在使用Flask-SQLAlchemy。我有两个通过关联表共享关系的类。当我尝试删除其中一个表中的行时。我看到以下错误:
sqlalchemy.orm.exc.StaleDataError
StaleDataError: DELETE statement on table 'tags' expected to delete 1 row(s); Only 2 were matched.
以下是我的模特:
tags = db.Table('tags',
db.Column('tag_id', db.Integer, db.ForeignKey('tag.id')),
db.Column('post_id', db.Integer, db.ForeignKey('posts.id'))
)
class Post(db.Model):
__tablename__ = 'posts'
id = db.Column(db.Integer, primary_key=True)
title = db.Column(db.String(255))
tags = db.relationship('Tag', secondary=tags,
backref=db.backref('posts', lazy='dynamic'))
def __init__(self, **kwargs):
super(Post, self).__init__(**kwargs)
def __repr__(self):
return '<title %r>' % self.title
class Tag(db.Model):
__tablename__ = 'tag'
id = db.Column(db.Integer, primary_key=True)
name = db.Column(db.String(120), unique=True)
这是我要删除的代码:
def remove_tag(tag_id):
tag = Tag.query.get(tag_id)
for post in tag.posts:
p = Post.query.get(post.id)
p.tags.remove(tag)
db.session.delete(tag)
db.session.commit()
我在这个应用程序之外的独立测试,数据库和环境中尝试了此代码的条带化版本。并且,它按预期工作,删除标记和关联的表行。
如果可能,我想知道:
提前感谢您的任何帮助。
最佳, 爱德华
答案 0 :(得分:0)
有一个顿悟!
我是如何处理StaleDataError的情况的?
在测试我的编辑帖子页面时,我对数据库做了很多相同帖子的POST。
当我对.all()的查询没有多次使用时,为什么它匹配多行?
我的测试在关联表中创建了多个条目。换句话说,我多次playerBody.angularDamping = 1;
次。
如何防止这种情况发生?
将唯一约束添加到关联表以停止对数据库的多个条目。我还在视图中添加了检查以停止多个条目。
playerBody.angularDamping = 0;
迁移您的数据库。
如果您使用SQlite和Alembic,您很可能会遇到此错误:“不支持SQLite方言中的ALTER约束”。有关此问题的更多信息,请访问here。
简而言之,如果这是一个开发数据库,则删除数据库会更容易。如果您在生产环境中,也许您应该考虑数据迁移并切换到另一个引擎。
答案 1 :(得分:0)
如果我无法修改标签并发布数据库模型(当我使用数据库迁移的开源项目时可能会导致很多问题),该怎么办?
我通过清除与tags
相关的post_id
来解决此问题,然后重置post.tags = []
,最后删除帖子
项目
1.
sql = text('delete from tags where post_id = %s' % post_id)
db.engine.execute(sql)
2.
post.tags = []
db.session.merge(post)
db.session.commit()
3.
db.session.delete(post)
db.session.commit()