如何在SQLAlchemy(python,flask)中为模型User创建多对多的关系

时间:2014-01-17 15:27:24

标签: python mysql flask many-to-many flask-sqlalchemy

我需要创建一个名为朋友的表格,它应该如下所示:

朋友:

  • USER_ID
  • friend_id

我试图用SQLALchemy的教程来做这件事,但我还没有找到如何为同一个表创建多对多的关系。

以下是我的尝试:

# friends table
# many to many - user - user
_friends = db.Table('friends',
    db.Column('user_id', db.Integer, db.ForeignKey('users.id')),
    db.Column('friend_id', db.Integer, db.ForeignKey('users.id'))
)


class User(db.Model, UserMixin):

    # table name in database
    __tablename__ = 'users'

    # primary key for table in db
    id = db.Column(db.Integer, primary_key=True)

    # email is unique!
    email = db.Column(db.String(255), unique=True)

    # password, max = 255
    password = db.Column(db.String(255))

    # category relation
    categories = relationship("Category")

    # cards relation
    cards = relationship("BusinessCard")

    # friends
    friends = db.relationship(
        'User',
        backref="users",
        secondary=_friends
    )

它说:

  

AmbiguousForeignKeysError:无法确定之间的连接条件   关系User.friends上的父/子表 - 有多个   通过辅助表'friends'链接表的外键路径。   指定'foreign_keys'参数,提供这些列的列表   应该将其视为包含来自的外键引用   每个父表和子表的辅助表。

有没有人知道如何正确地做到这一点?

3 个答案:

答案 0 :(得分:8)

您尝试实施的模式是多对多关系的特例。 SQLAlchemy称之为邻接列表关系,我建议尝试在那里完成代码:

http://docs.sqlalchemy.org/en/rel_0_9/orm/relationships.html#adjacency-list-relationships

关键是那里的'remote_side'kwarg。

原因如下:您得到的错误是因为您的关联表('friends')有两个指向表'users'的外键:一个在'user_id'列上,另一个在'friend_id'列上。 SQLAlchemy尝试基于外键自动检测关系,但它失败了,因为它无法分辨关系的方向。所以,如果你在表'朋友'中有一个条目,那么

user_id   : 1
friend_id : 2

SQLAlchemy无法判断user_1是否将user_2作为好友,反之亦然。

如果这看起来令人困惑,那就是。社交网络意义上的友谊可以是单一的,在这种情况下,具有朋友user_2的user_1并不意味着user_2将user_1作为朋友;或者它可以是双射,在这种情况下,两者是等价的。我在这里展示我的年龄,但前者由Livejournal代表,而后者则由Facebook代表。

我不知道如何在SQLAlchemy中实现一个单一的关系。这是一个丑陋的UNION ALL或MySQL中的类似内容。

答案 1 :(得分:6)

答案 2 :(得分:1)

您不能直接在2个表之间建立多对多关系,而是必须使用第3个表。 enter image description here