Flask-SQLAlchemy中的db.Model与db.Table [英] db.Model vs db.Table in Flask-SQLAlchemy

查看:477
本文介绍了Flask-SQLAlchemy中的db.Model与db.Table的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

Flask-SQLAlchemy文档说多对多查找表不应子类db.Model,而应被编写为db.Tables.从文档中:

The Flask-SQLAlchemy docs say that many-to-many lookup tables should not subclass db.Model but instead be written as db.Tables. From the docs:

如果要使用多对多关系,则需要定义 用于该关系的帮助器表.对于这个帮手 强烈建议您不要使用模型,而是使用实际 桌子

If you want to use many-to-many relationships you will need to define a helper table that is used for the relationship. For this helper table it is strongly recommended to not use a model but an actual table

为什么?使一切成为模型的不利之处是什么?我认为采用统一的方式在数据库中声明表看起来更干净.另外,有可能以后某个时间,开发人员将需要直接访问这些映射记录,而不是通过需要模型的关系来访问.

Why? What are the downsides to making everything a model? I think it looks cleaner to have a unified way of declaring tables in the database. Also, it's possible that sometime later a developer will want to access those mapping records directly, rather than through a relationship, which would require a model.

推荐答案

db.Table更简单.

The db.Table is more simple.

当您通过db.Table定义多对多关系时,SQLAlchemy将接替您并完成大部分工作.

When you define a many-to-many relationship through db.Table, SQLAlchemy would take over and do most of the job for you.

因此,假设我们与具有以下TableModel定义的帖子和标签有关系:

So, assuming that we have a relationship with posts and tags with the following Table and Model definitions:

表格:

tagging = db.Table('tagging',
    db.Column('post_id', db.Integer, db.ForeignKey('post.id')),
    db.Column('tag_id', db.Integer, db.ForeignKey('tag.id'))
)

型号:

class Tagging(db.Model):
    tag_id = db.Column(db.Integer, db.ForeignKey('tag.id'),
                              primary_key=True)
    post_id = db.Column(db.Integer, db.ForeignKey('post.id'),
                               primary_key=True)

插入和删除

文档:

relationship()的第二个参数所独有的行为是,在添加或从集合中删除对象时,此处指定的表会自动受到INSERT和DELETE语句的约束.无需手动从该表中删除.从集合中删除记录的行为将使行在刷新时被删除.

A behavior which is unique to the secondary argument to relationship() is that the Table which is specified here is automatically subject to INSERT and DELETE statements, as objects are added or removed from the collection. There is no need to delete from this table manually. The act of removing a record from the collection will have the effect of the row being deleted on flush.

使用db.Table,您可以执行以下操作:

With db.Table, you can do something like this:

>>> post.tags.append(tag_foo)
>>> db.session.commit()

您无需将其添加到会话中,则可以使用remove()删除关系:

You needn't add it into session, then you can delete a relationship with remove():

>>> post.tags.remove(tag_foo)
>>> db.session.commit()

但是,如果使用db.Model,则必须执行以下操作(Tagging是Model类):

However, if you use db.Model, you have to do something like this (Tagging is the Model class):

>>> tagging = Tagging(post=post_foo, tag=tag_bar)
>>> db.session.add(tagging)
>>> db.session.commit()

然后将其删除,如下所示:

then delete it like this:

>>> tagging = post.tags.filter_by(post_id=post.id).first()
>>> db.session.delete(tagging)
>>> db.session.commit()

查询

使用db.Table:

>>> post.tags.all()
>>> [<Tag 'foo'>, ...]

然后db.Model:

>>> post.tags.all()  # You only get Tagging item.
>>> [<Tagging 'post_foo -- tag_bar'>, ...]
>>> for tagging in post.tags:
>>>     print tagging.tag  # <Tag 'foo'>

总之,如果您不需要存储有关该关系的额外数据,只需使用db.Table,它将节省您的时间.

In a word, if you don't need to store extra data about the relationship, just use db.Table, it will save your time.

这篇关于Flask-SQLAlchemy中的db.Model与db.Table的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆