首页 > 解决方案 > 从用户表继承的最佳方式(SQLAlchemy & UserMixin)

问题描述

我有一个 SQLALchemy 表:

class User(db.Model, UserMixin):
    user_id = db.Column(db.Integer, primary_key=True)
    username = db.Column(db.String(100), nullable=False, unique=True)
    password_hash = db.Column(db.String(40), nullable=False)

但我希望用户能够通过使用用户名和密码创建新帐户或使用社交媒体帐户 (google/twitter/vk.com) 来登录和注册。我的想法是有一个基本的 User 表,该表将具有像 get_name() 这样的抽象方法,必须在每个社交媒体的派生表中定义这些方法。

伪代码:

基础用户

class User(db.Model, UserMixin):
    user_id = db.Column(db.Integer, primary_key=True)

    # Overridden method from UserMixin
    def get_id(self):
        return self.user_id

    def get_name(self): raise NotImplementedError

谷歌用户

class GoogleUser(User):

    first_name = db.Columnn(db.String(40), nullable=False)
    last_name = db.Columnn(db.String(40), nullable=False)

    def get_name(self):
        return '{} {}'.format(self.first_name, self.last_name)

电子邮件用户

class EmailUser(User):
    username = db.Column(db.String(100), nullable=False, unique=True)
    password_hash = db.Column(db.String(40), nullable=False)

    def get_name(self):
        return self.username

问题是用 SQLAlchemy 和 UserMixin 实现它的最佳方法是什么?感谢您提前提供任何帮助。

标签: pythonflasksqlalchemy

解决方案


我通常做的是创建一个User包含应用程序所需的所有信息的模型,例如

class User(db.Model, UserMixin):
    user_id = db.Column(db.Integer, primary_key=True)
    username = db.Column(db.String(100), nullable=False, unique=True)
    password_hash = db.Column(db.String(40), nullable=True)

然后对于第三方服务身份验证,我创建了一个表,用于存储令牌和其他有关应用程序需要的服务的相关数据,例如

class GoogleUser(db.Model):

    first_name = db.Column(db.String(40), nullable=False)
    last_name = db.Column(db.String(40), nullable=False)
    google_token = db.Column(db.String(200), nullable=False)

我通过外键将这个新表连接到User模型:

google_user_id = db.Column(db.Integer, db.ForeignKey("google_user.id"))

这样,用户可以轻松连接他们的第三方帐户并在您的应用程序上拥有一个帐户。

Facebook Login 的文档也建议这样做

希望它能解决问题!


推荐阅读