2

我们有一个使用“多模式”策略的多租户 SaaS 应用程序,即每个客户在同一个数据库实例中都有专用的模式。我们使用 MS SQL Server 作为数据库,它通过 SQL Server“用户”的“默认模式”设置在模式之间切换。例如客户 A、B 和 C 在 SQL Server 中配置如下:

  • 客户 A:user_A使用默认架构schema_A
  • 客户 B:user_B使用默认架构schema_B
  • 客户 C:user_C使用默认模式schema_C……等等。

在我们的应用程序中,我们通过在每次查询之前执行以下 SQL 在连接上设置 SQL Server“用户”,将 DataSource 连接切换为指向每个客户的正确模式:

EXECUTE AS USER = 'user_A';

在尝试使用 Flyway 以全局方式管理模式版本的状态时,这给我们带来了一些问题。由于 flyway 的架构支持仅接受架构名称列表,因此这不适用于 MS SQL Server。Flyway 在 DataSource 配置提供的用户的默认模式上执行迁移;在 SQL Server 的情况下,“用户”需要因客户/模式而异。

理想情况下,我们会有一个这样的回调FlywayCallback.beforeEachSchemaMigrate(Connection),让我们通过在每个模式的每次迁移之前执行“以用户身份执行”语句来设置每个模式所需的用户上下文。不知道为什么没有那个钩子?

flyway 的另一个缺点是在模式列表中使用第一个模式的约定,作为持有schema_version表的模式。这在基于 SQL Server 的多租户环境中是不需要的。因为我们不能假设包含schema_version表的模式也是真正的客户模式。请记住,在像我们这样的 SaaS 应用程序中,每个租户/客户的模式是动态创建/销毁的。当用户注册时,配置过程的一部分会根据一些约定创建新模式。所以模式列表对我们来说是动态的。

理想情况下,我们可以告诉 Flyway 使用给定的模式来创建schema_version表,而无需尝试在该模式上运行迁移。通常这将是dbo架构(这是 SQL Server 中的默认架构)。我们使用 dbo 模式来保存跨所有租户的全局表,schema_version 将被视为全局表。

所以最终在成功迁移后,我们的数据库应该如下所示:

 - dbo.schema_version
 - schema_A.my_tables
 - schema_B.my_tables
 - schema_C.my_tables

上述所有模式都处于相同的“状态”,由dbo.schema_version表指示和控制。

这目前可能吗?

4

1 回答 1

1

你必须以不同的方式处理问题。与其为每个人执行一次 Flyway,不如为每个模式执行一次。您可以将 Flyway 包装在一个循环中,并在每次迭代时为一个租户提供正确的配置。您最终将得到每个租户一个 schema_version 表,但它们都可以单独命名并且仍然存在于 dbo 模式中。

于 2014-07-16T08:19:36.793 回答