【问题标题】:Row/Column Based Multi-Tenancy in SQLAlchemy using a Shared Schema使用共享模式的 SQLAlchemy 中基于行/列的多租户
【发布时间】:2021-05-05 15:34:31
【问题描述】:

我想使用 Flask + SQLAlchemy 构建一个多租户应用程序。官方 SQLAlchemy 文档 suggest that,要使用多租户,表应该分布在每个租户的 1 个方案上,并在引擎级别处理不同的租户。

维护多个方案对我来说似乎有点臃肿,我想知道如果设计正确,以下对所有租户使用相同表的方法是否可行,如果不可行,为什么不:

  • 那些包含租户拥有记录的表有一个不可为空的列tenant_id,指示哪个租户“拥有”该行。
  • 创建/更新语句(INSERTUPDATE)自动将此列的值设置为当前租户。
  • 读取/删除查询(SELECTDELETE)查询会自动将 WHERE tenant_id=:current tenant 子句/过滤器添加到 SQL。
  • tenant_id 的值可以从 JSON Web Token 派生。
  • 这个自动设置的 value/where 子句可以在后台管理,例如通过this answer 中的自定义会话或使用预提交挂钩。

我几乎找不到关于这种方法的任何信息(除了这个名为 MultiAlchemy 的软件包,它的工作原理似乎与我的描述相似,但已存档且 7 年未更新)。我的直觉告诉我,这是有原因的。

tl;dr:为什么不在 SQLAlchemy 中使用共享方案进行多租户?

【问题讨论】:

    标签: sqlalchemy flask-sqlalchemy multi-tenant


    【解决方案1】:

    您可能已经发现(包括该问题的其他答案),多租户实施有多种方法,各有优缺点,没有明显的赢家。 What is Multi-Tenant Architecture 只是另一个,但很好地概述了几个选项,我不会从中复制,因为阅读整篇文章是有意义的。

    所有方法的优缺点都取决于团队的个人偏好和经验。


    就我个人而言,我非常希望扩展sqlalchemy 来实现单一共享数据库架构 多租户,即MultiAlchemy。目前尚不清楚为什么该项目被存档,但我有兴趣创建一个新项目来支持此功能,基于:

    【讨论】:

    • @konstantin: 如果你决定实现这个(并且有一个真正的测试用例),我可能会很乐意支持开发这样的扩展,因为它会引起我的兴趣在我的下一个项目中
    【解决方案2】:

    这是多租户的两种不同方法:

    • 1-scheme-per-tenant 看起来像 public.companies, company_a.users, company_a.posts, company_b.users, company_b.posts, ... 并且在这些表中没有对实际租户(公司)的引用
      • 它非常适合在多个数据库之间分配数据
      • 当添加/删除租户是非常罕见的事件时,它会更好地工作,因为这是一个有点复杂的过程(创建新架构等)
      • 在架构/数据库管理方面需要额外的努力
      • 跨租户请求难以实现
    • 共享模式看起来像一组固定的表public.companies, public.users, public.posts,并且表将包含对实际租户的引用(例如company_id)
      • 添加/删除租户是一个非常简单的过程
      • 单一架构需要较少的管理
      • 跨租户请求很简单
      • 这种方法难以在数据库之间扩展或分布

    我想说这主要取决于租户的数量和数据大小。少数租户,但有大量数据,那么第一种方法肯定更好。动态租户数量,则第二种方法更好。

    我之前没有见过第二种方法的一般实现,比如MultiAlchemy,我个人会尝试一下。

    【讨论】:

      【解决方案3】:

      如果您使用多个模式来分离不同租户的数据,您基本上是在改进:

      1. 安全性,因为单独的架构允许为每个租户拥有单独的数据库用户。如果在数据库级别已经不可能访问不同租户的数据,您不必依赖使用数据库的软件来仅访问租户应该有权访问的数据。这显着降低了程序员忘记 WHERE 子句/SQLAlchemy 过滤器的可能性,该过滤器限制了对当前租户数据的访问。

      2. 可扩展性,因为您可以轻松地将已经分离的模式分布在多个服务器上,而不是单个表上。因此,如果您为不同的租户使用不同的架构,那么您已经在为未来的增长做准备。

      如果您仅使用专用外键列对多个租户和数据所有权进行建模,则不会给出这两个方面。

      【讨论】:

        猜你喜欢
        • 2020-02-02
        • 2019-05-18
        • 2020-06-26
        • 2018-02-20
        • 2014-01-16
        • 2012-11-02
        • 2014-03-21
        • 2022-09-27
        • 1970-01-01
        相关资源
        最近更新 更多