你当前正在访问 Microsoft Azure Global Edition 技术文档网站。 如果需要访问由世纪互联运营的 Microsoft Azure 中国技术文档网站,请访问 https://docs.azure.cn

多租户解决方案中存储和数据的体系结构方法

数据通常被视为解决方案中最有价值的部分,因为它代表你和你的客户有价值的业务信息。 请务必仔细管理数据。 为多租户系统规划存储或数据组件时,需要确定共享或隔离租户数据的方法。

本文提供有关解决方案架构师在决定在多租户系统中存储数据的方法时的关键注意事项和要求的指导。 本文还介绍了一些常见模式,这些模式用于将多租户应用于存储和数据服务,以及一些要避免的反模式。 它还针对某些特定方案提供有针对性的指导。

关键考虑因素和要求

请务必从多个角度考虑用于存储和数据服务的方法,包括 Azure Well-Architected 框架的支柱。

规模

使用存储数据的服务时,应考虑拥有的租户数和存储的数据量。 如果租户很少(例如 5 个或更少),并且为每个租户存储少量数据,则可能需要规划高度可缩放的数据存储方法或构建一种完全自动化的方法来管理数据资源。

但是,随着增长,你越来越受益于拥有一个明确的策略来缩放数据和存储资源并自动执行其管理。 如果拥有 50 个租户或更多租户,或者你计划达到该规模级别,那么设计数据和存储方法尤其重要,以缩放作为关键考虑因素。

考虑计划缩放的程度,并明确规划数据存储体系结构方法以满足该缩放级别。

性能可预测性

多租户数据和存储服务容易受到 干扰邻居问题的影响。 需考虑租户是否可能会影响彼此的性能,这十分重要。 例如,请考虑租户在一段时间内的使用模式中是否有重叠的峰值。 还要考虑所有客户是否每天同时使用解决方案,以及请求是否均匀分布。 这些因素会影响需要设计的隔离级别、预配的资源量以及租户可以共享资源的程度。

请务必考虑 Azure 资源和请求配额 作为此决定的一部分。 例如,假设部署单个存储帐户以包含租户的所有数据。 如果每秒超过特定数量的存储作,Azure 存储会拒绝应用程序的请求,这会影响所有租户。 此行为称为 限制。 对受限制的请求进行监视会十分重要。

数据隔离

在设计包含多租户数据服务的解决方案时,有不同的选项和数据隔离级别具有自身优势和权衡。 请考虑以下示例:

  • 使用 Azure Cosmos DB 时,可以为每个租户部署单独的容器,并且可以在多个租户之间共享数据库和帐户。 或者,可以考虑为每个租户部署不同的数据库,甚至为每个租户部署帐户,具体取决于所需的隔离级别。

  • 将存储用于 Blob 数据时,可以为每个租户部署单独的 Blob 容器,也可以部署单独的存储帐户。

  • 使用 Azure SQL 时,可以在共享数据库中使用单独的表,也可以为每个租户部署单独的数据库或服务器。

  • 在所有 Azure 服务中,可以考虑在单个共享 Azure 订阅中部署资源,也可以使用多个 Azure 订阅,甚至为每个租户使用一个订阅。

没有适用于每个方案的单一解决方案。 选择的选项取决于多种因素和租户的要求。 例如,如果设计企业对消费者(B2C)解决方案,则为所有数据使用单个数据存储可能很合理。 但是,如果你的租户需要满足特定的合规性或法规标准,则可能需要应用更高级别的隔离。

同样,你可能有商业要求来物理隔离客户的数据,或者可能需要强制隔离以避免 干扰邻居问题。 如果满足以下任一条件,可能需要将租户与其他租户隔离,或者将其与具有类似策略的租户分组:

  • 租户需要使用自己的加密密钥
  • 租户具有单独的备份和还原策略
  • 租户需要将数据存储在不同的地理位置

实现的复杂性

考虑实现的复杂性会十分重要。 最好尽可能简单地保持体系结构,同时仍满足要求。 避免在缩放或没有开发和维护资源或专业知识的体系结构时提交到可能越来越复杂的体系结构。

同样,如果解决方案不需要扩展到大量租户,或者你不关心性能或数据隔离,则最好保持解决方案简单,避免增加不必要的复杂性。

多租户数据解决方案的一个特别关注点是你支持的自定义级别。 例如,可以允许租户扩展数据模型或应用自定义数据规则。 请确保提前针对此要求进行设计。 避免为单个租户分叉或提供自定义基础结构。 自定义的基础结构不支持进行缩放、测试解决方案,或部署更新。 相反,请考虑使用 功能标志 和其他形式的租户配置。

管理和操作的复杂性

请考虑你计划如何作解决方案,以及多租户方法如何影响作和流程。

  • 管理: 考虑管理作,例如定期维护活动。 如果使用多个服务器、文件存储或数据库,请计划如何为每个租户的资源启动和监视维护作。

  • 监视和计量: 如果监视或计量租户,请考虑解决方案如何报告指标,以及它是否可以轻松地将指标链接到触发请求的租户。

  • 报告: 考虑是否需要报告来自多个独立租户的聚合数据。 随着解决方案的扩展,单独对每个数据库运行查询并聚合结果会变得麻烦。 不同的方法是让每个租户的应用程序将数据发布到集中式数据仓库。

  • 架构更新: 如果使用强制实施架构的数据库,请计划如何在资产中部署架构更新。 考虑应用程序如何知道要用于特定租户的数据库查询的架构版本。

  • 要求: 考虑租户的高可用性要求,例如运行时间服务级别协议(SLA)和灾难恢复要求,例如恢复时间目标(RTO)和恢复点目标(RPO)。 如果租户具有不同的预期,请验证是否可以满足每个租户的要求。

  • 迁移: 请考虑是否要让租户移动到不同类型的服务、不同的部署或其他区域。 如果计划提供此功能,请生成流程和工具,以确保它是可重复且安全的流程。

成本

通常,部署基础结构的租户密度越高,预配该基础结构的成本就越低。 但是,共享基础结构增加了 干扰邻居问题等问题的可能性,因此请仔细考虑权衡。

要考虑的方法和模式

Azure 体系结构中心的多个设计模式与多租户存储和数据服务相关。 可以选择始终遵循一种模式。 或者,可以考虑混合和匹配模式。 例如,对于大多数租户,可以使用多租户数据库,但为支付更多或有异常要求的租户部署单租户戳。

部署戳模式

有关如何使用 部署标记模式 支持多租户解决方案的详细信息,请参阅 概述

小窍门

在多租户解决方案中,最好创建部署标记。 即使在标记中使用多租户数据库或分片数据库时,此建议也适用。 通过将解决方案建模为标记,可以轻松重新部署解决方案,因为新的商机出现。

共享多租户数据库和文件存储

可以考虑部署共享多租户数据库、存储帐户或文件共享,并在所有租户之间共享。

显示所有租户数据的单个共享多租户数据库的关系图。

此方法为基础结构提供了租户的最高密度,因此它往往以任何方法的最低财务成本提供。 它还通常会减少管理开销,因为有一个数据库或资源来管理、备份和安全。

但是,使用共享基础结构时,请考虑以下缺点:

  • 规模限制: 依赖单个资源时,请考虑该资源支持的缩放和限制。 例如,如果体系结构依赖于单个共享数据库、数据库或文件存储的最大大小或最大吞吐量限制,最终会成为硬阻止程序。 在选择此模式之前,请仔细考虑需要实现的最大规模并将其与当前和将来的限制进行比较。

  • 干扰邻居:干扰性邻居问题可能会成为一个因素,尤其是在租户繁忙或生成比其他人更高的工作负荷时。 请考虑应用 限制模式速率限制模式 来缓解这些影响。

  • 度量租户的使用情况: 考虑是否需要度量每个租户的 消耗 量。 某些数据服务(例如 Azure Cosmos DB)提供每个事务的资源使用情况报告。 可以跟踪此信息并将其聚合,以度量每个租户的消耗量。 其他服务不提供相同级别的详细信息。 例如,将 Azure 文件与高级文件共享配合使用时,可以访问每个文件共享维度的文件容量指标。 标准层仅在存储帐户级别提供指标。

  • 租户要求: 租户在安全性、备份、可用性或存储位置方面可能有不同的要求。 如果这些要求与单个资源的配置不匹配,则可能无法容纳这些要求。

  • 架构自定义: 使用关系数据库或其他数据架构非常重要的方案时,租户级架构自定义将很困难。

分片模式

分片模式涉及部署多个单独的数据库(称为分片),每个数据库都包含一个或多个租户的数据。 与部署标记不同,分片并不意味着整体基础架构被完全复制。 可以对数据库进行分片,而不对解决方案中的其他基础结构进行复制或分片。

显示分片数据库的关系图。一个数据库包含租户 A 和 B 的数据,另一个数据库包含租户 C 的数据。

分片与 分区密切相关,术语通常可互换使用。 请考虑水平数据分区、垂直数据分区和功能数据分区指导

分片模式可以扩展到大量租户。 根据工作负荷,你可能还可以实现向分片的高密度租户,从而降低成本。 可以使用分片模式解决 Azure 订阅和服务配额、限制和约束

某些数据存储(例如 Azure Cosmos DB)可为分片或分区提供本机支持。 使用其他解决方案(例如 Azure SQL)时,构建分片基础结构并将请求路由到给定租户的正确分片可能更为复杂。

分片还使得支持租户级配置差异变得困难,并使客户能够提供自己的加密密钥。

每个租户各有专用数据库的多租户应用

另一种常见方法是部署具有每个租户专用数据库的单个多租户应用程序。

显示每个租户的不同数据库的关系图。

在此模型中,每个租户的数据都与其他租户的数据隔离开来,并且你可能能够为每个租户支持某种程度的自定义。

此方法的成本可能高于共享托管模型,因为为每个租户预配专用数据资源。 但是,Azure 提供了多个选项,可以考虑跨多个租户共享托管单个数据资源的成本。 例如,使用 Azure SQL 数据库时,可以考虑 弹性池。 对于 Azure Cosmos DB,可以为 数据库预配吞吐量,吞吐量在该数据库中的容器之间共享。 但是,当你需要保证每个容器的性能时,此方法不适用。

在此方法中,由于仅为每个租户单独部署数据组件,因此你可能可以为解决方案中的其他组件实现较高密度,并降低这些组件的成本。

注释

为每个租户预配数据库时,请务必使用自动部署方法。 否则,手动部署和管理数据库的复杂性将变得压倒性。

地理节点模式

Geode 模式专为地理分布式解决方案设计,包括多租户解决方案。 它支持高负载和高级别的复原能力。 如果实现 Geode 模式,数据层必须能够跨地理区域复制数据,并且它应支持多地理位置写入。

显示 Geode 模式的关系图,其中部署的数据库跨多个区域同步。

Azure Cosmos DB 提供 多区域写入 来支持此模式,适用于 Apache Cassandra 的 Azure 托管实例支持 多区域群集。 其他数据服务通常不支持此模式,而无需进行重大自定义。

要避免的反模式

创建多租户数据服务时,需避免使你无法缩放的情况,这十分重要。

对于关系数据库,这些反模式包括:

  • 基于表的隔离。 在单个数据库中工作时,请避免为每个租户创建单个表。 使用此方法时,单个数据库无法支持大量租户,因此查询、管理和更新数据变得越来越困难。 相反,请考虑使用具有租户标识符列的单个多租户表集。 或者,可以使用 建议的模式 为每个租户部署单独的数据库。

  • 列级别租户自定义。 避免只适用于单一租户的架构更新。 例如,假设你有一个多租户数据库。 避免添加新列以满足特定租户的要求。 对于一些自定义项,此方法可能可以接受,但当你需要考虑许多自定义项时,此方法会很快变得不可管理。 相反,请考虑修改数据模型以在专用表中跟踪每个租户的自定义数据。

  • 手动更改架构。 即使只有单个共享数据库,也需避免手动更新数据库架构。 很容易失去对应用的更新的跟踪,如果需要横向扩展到更多数据库,则很难确定要应用的正确架构。 而是生成工具或自动化管道来部署架构更改,并一致地使用它。 跟踪专用数据库或查阅表中每个租户使用的架构版本。

  • 版本依赖项。 避免让应用程序依赖于单一版本的数据库架构。 进行缩放时,可能需要在不同时间为不同租户应用架构更新。 相反,请确保应用程序版本与至少一个以前的架构版本向后兼容,并跨多个版本对破坏性架构更改进行排序以支持回滚。

数据库

有一些功能可用于多租户。 但是,这些功能在所有数据库服务中都不可用。 在决定服务用于方案时,请考虑是否需要以下功能:

  • 行级别安全性 可以为共享多租户数据库中的特定租户数据提供安全隔离。 此功能在某些数据库中可用,例如 SQL 数据库和 Azure Database for PostgreSQL 灵活服务器。

    使用行级安全性时,需要确保用户的标识和租户标识通过应用程序传播,并通过每个查询传播到数据存储中。 此方法可能非常复杂,可以设计、实现、测试和维护。 由于这些复杂性,许多多租户解决方案不使用行级安全性。

  • 可能需要租户级加密来支持为其数据提供自己的加密密钥的租户。 此功能在 SQL Server 和 Azure SQL 中作为 Always Encrypted 的一部分提供。 Azure Cosmos DB 提供帐户级别的客户管理的密钥,并且支持 Always Encrypted

  • 利用资源池 ,可以在多个数据库或容器之间共享资源及其成本。 此功能适用于 SQL 数据库 弹性池Azure SQL 托管实例和 Azure Cosmos DB 数据库吞吐量

  • 分片和分区 在某些服务中具有比其他服务更强大的本机支持。 此功能在 Azure Cosmos DB 中使用其 逻辑分区和物理分区。 尽管 SQL 数据库本身不支持分片,但它提供 分片工具 来支持这种类型的体系结构。

此外,在维护关系数据库或其他基于架构的数据库群时,请考虑应触发架构升级过程的位置。 在小型数据库中,你可能会考虑使用部署管道部署架构更改。 随着数据库数量的增加,应用程序层最好能检测特定数据库的模式版本并启动升级过程。

文件和 blob 存储

请考虑用于隔离存储帐户中的数据的方法。 例如,可以为每个租户部署单独的存储帐户,也可以共享存储帐户并部署单个容器。 或者,可以创建共享 blob 容器,然后使用 blob 路径分隔每个租户的数据。 考虑 Azure 订阅限制和配额,并仔细规划增长,以确保 Azure 资源缩放以支持将来的需求。

如果使用共享容器,请仔细规划身份验证和授权策略,以确保租户无法访问彼此的数据。 向客户端提供对存储资源的访问权限时,请考虑 辅助密钥模式

成本分配

请考虑如何 衡量消耗量,以及如何向租户分配成本 ,以便使用共享数据服务。 尽可能使用内置指标,而不是计算自己的指标。 但是,使用共享基础结构时,很难拆分单个租户的遥测数据,因此可能需要考虑使用应用程序级自定义计量。

通常,云原生服务(如 Azure Cosmos DB 和 Azure Blob 存储)可提供更精细的指标,用于对特定租户的使用情况进行跟踪和建模。 例如,Azure Cosmos DB 提供每个请求和响应消耗的吞吐量。

供稿人

Microsoft维护本文。 以下参与者撰写了本文。

主要作者:

  • John Downs |Azure 模式和做法的主要软件工程师

其他参与者:

若要查看非公开的LinkedIn个人资料,请登录LinkedIn。

有关多租户和特定 Azure 服务的详细信息,请参阅以下资源: