多租户 SQL 服务器数据库中的复合主键
Composite primary key in multi-tenant SQL Server database
我正在使用 ASP.NET Web Api、Entity Framework 和 SQL 服务器/Azure 数据库构建多租户应用程序(单一数据库、单一架构)。
此应用将被 1000-5000 位客户使用。所有 table 都有一个 TenantId
(Guid
) 列。现在,我使用单列主键 Id
(Guid
)。
问题在于,我必须检查用户提供的数据是否来自/针对正确的租户。例如,我有一个销售订单 table,其中有一个 CustomerId
列。每次用户 post/update 销售订单,我都必须检查 CustomerId
是否来自同一个租户。
情况变得更糟,因为每个租户可能有多个网点。然后我必须检查 TenantId 和 OutletId。这真是一场维护噩梦,对性能不利。
我正在考虑添加 TenantId
作为主键以及 Id
。也可能添加 OutletId
。因此销售订单 table 中的主键将有多个列,Id
、TenantId
、OutletId
。
这种方法的缺点是什么?使用复合键会严重损害性能吗?复合键顺序重要吗?我的问题有更好的解决方案吗?
如果你想使用复合键,请始终(如果可能)使用键的所有元素以避免 index range scans
元素的顺序很重要。例如,如果您想检索与单个租户相关的所有数据(请参阅第 1 部分),您应该使用 TenantId
作为第一个元素(请参阅 Why does primary key order matter?)
对于 Azure SQL,您还应该考虑 Elastic Scale 等概念或对遗留系统进行分区以提高性能。
您真的需要 TenantId 的 guid 吗?如果您的客户数量有限(<= 5000 不是那么多),您还可以使用 int(甚至 int64)类型,这样可以更轻松地进行分区(参见第 3 部分)...我非常喜欢 guid,但为了便于维护,如果我不需要大范围的数据,我会尽量避免使用它们(请参阅 this article 了解性能)。如果提前需要租户id,可以使用sequences(SQL Azure V12的新特性):
create sequence CustomerSequence as int
start with 0
increment by 1;
select next value for CustomerSequence;
编辑: 在 SQL Azure
中添加了有关序列的信息
我正在使用 ASP.NET Web Api、Entity Framework 和 SQL 服务器/Azure 数据库构建多租户应用程序(单一数据库、单一架构)。
此应用将被 1000-5000 位客户使用。所有 table 都有一个 TenantId
(Guid
) 列。现在,我使用单列主键 Id
(Guid
)。
问题在于,我必须检查用户提供的数据是否来自/针对正确的租户。例如,我有一个销售订单 table,其中有一个 CustomerId
列。每次用户 post/update 销售订单,我都必须检查 CustomerId
是否来自同一个租户。
情况变得更糟,因为每个租户可能有多个网点。然后我必须检查 TenantId 和 OutletId。这真是一场维护噩梦,对性能不利。
我正在考虑添加 TenantId
作为主键以及 Id
。也可能添加 OutletId
。因此销售订单 table 中的主键将有多个列,Id
、TenantId
、OutletId
。
这种方法的缺点是什么?使用复合键会严重损害性能吗?复合键顺序重要吗?我的问题有更好的解决方案吗?
如果你想使用复合键,请始终(如果可能)使用键的所有元素以避免 index range scans
元素的顺序很重要。例如,如果您想检索与单个租户相关的所有数据(请参阅第 1 部分),您应该使用
TenantId
作为第一个元素(请参阅 Why does primary key order matter?)对于 Azure SQL,您还应该考虑 Elastic Scale 等概念或对遗留系统进行分区以提高性能。
您真的需要 TenantId 的 guid 吗?如果您的客户数量有限(<= 5000 不是那么多),您还可以使用 int(甚至 int64)类型,这样可以更轻松地进行分区(参见第 3 部分)...我非常喜欢 guid,但为了便于维护,如果我不需要大范围的数据,我会尽量避免使用它们(请参阅 this article 了解性能)。如果提前需要租户id,可以使用sequences(SQL Azure V12的新特性):
create sequence CustomerSequence as int start with 0 increment by 1; select next value for CustomerSequence;
编辑: 在 SQL Azure
中添加了有关序列的信息