繁体   English   中英

Flask SQLAlchemy:将第三列添加到连接表

[英]Flask SQLAlchemy: adding third column to joining table

上下文:我正在制作一个使用 Flask-SQLAlchemy 的拍卖网站。 我的表需要有多对多的关系(因为一件艺术品可以有多个用户出价,而一个用户可以对多个艺术品出价)

我的问题是:可以在我的连接表中添加另一列以包含用户出价的 id、他们正在出价的艺术品的 id 以及他们出价多少? 另外,如果是,当我向所述表格添加记录时,我将如何将此出价包含在表格中?

bid_table = db.Table("bid_table",
db.Column("user_id", db.Integer, db.ForeignKey("user.user_id")),
db.Column("item_id", db.Integer, db.ForeignKey("artpiece.item_id"))
)


class User(db.Model):
    user_id = db.Column(db.Integer, unique=True, primary_key=True, nullable=False)
    username = db.Column(db.Integer, unique=True, nullable=False)
    email = db.Column(db.String(50), unique =True, nullable=False)
    password = db.Column(db.String(60), nullable=False)
    creation_date = db.Column(db.DateTime, default=str(datetime.datetime.now()))
    bids = db.relationship("Artpiece", secondary=bid_table, backref=db.backref("bids", lazy="dynamic"))


class Artpiece(db.Model):
    item_id = db.Column(db.Integer, unique=True, primary_key=True, nullable=False)
    artist = db.Column(db.String(40), nullable=False)
    buyer = db.Column(db.String(40), nullable=False)
    end_date = db.Column(db.String(40))
    highest_bid = db.Column(db.String(40))

使用 SQL Alchemy 可以做到这一点,但在我看来它非常麻烦。

SQLAlchemy 使用称为关联代理的概念将普通表转换为关联表。 这个表可以有你想要的任何数据字段,但你必须手动告诉 SQLAlchemy 哪些列是其他两个相关表的外键。

这是文档中的一个很好的例子。

在您的情况下, UserKeyword表是您要为您的用户/出价方案构建的关联代理表。

special_key列是您要存储的任意数据,例如出价金额。

from sqlalchemy import Column, Integer, String, ForeignKey
from sqlalchemy.ext.associationproxy import association_proxy
from sqlalchemy.orm import backref, declarative_base, relationship

Base = declarative_base()

class User(Base):
    __tablename__ = 'user'
    id = Column(Integer, primary_key=True)
    name = Column(String(64))

    # association proxy of "user_keywords" collection
    # to "keyword" attribute
    keywords = association_proxy('user_keywords', 'keyword')

    def __init__(self, name):
        self.name = name

class UserKeyword(Base):
    __tablename__ = 'user_keyword'
    user_id = Column(Integer, ForeignKey('user.id'), primary_key=True)
    keyword_id = Column(Integer, ForeignKey('keyword.id'), primary_key=True)
    special_key = Column(String(50))

    # bidirectional attribute/collection of "user"/"user_keywords"
    user = relationship(User,
                backref=backref("user_keywords",
                                cascade="all, delete-orphan")
            )

    # reference to the "Keyword" object
    keyword = relationship("Keyword")

    def __init__(self, keyword=None, user=None, special_key=None):
        self.user = user
        self.keyword = keyword
        self.special_key = special_key

class Keyword(Base):
    __tablename__ = 'keyword'
    id = Column(Integer, primary_key=True)
    keyword = Column('keyword', String(64))

    def __init__(self, keyword):
        self.keyword = keyword

    def __repr__(self):
        return 'Keyword(%s)' % repr(self.keyword)

查看完整文档以获取有关如何访问和创建此类模型的说明。

在实际项目中使用过它,它并不是特别有趣,如果您可以避免它,我会推荐它。

https://docs.sqlalchemy.org/en/14/orm/extensions/associationproxy.html

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM