多租户:每个租户的单个数据库

我们正在开发一个多租户应用程序。 在架构方面,我们为业务逻辑设计了共享中间层,为每个租户设计了一个数据持久性数据库。 如果说,业务层将与每个租户的数据库服务器建立连接集(连接池)。 这意味着应用程序为每个租户维护单独的连接池。 如果我们期望大约5000个租户,那么此解决方案需要高资源利用率(每个租户的应用服务器和数据库服务器之间的连接),这会导致性能问题。

我们通过保持公共连接池来解决这个问题。 为了在不同的数据库中维护单个连接池,我们创建了一个名为“App-master”的新数据库。 现在,我们始终首先连接到“App-master”数据库,然后将数据库更改为特定于租户的数据库。 这解决了我们的连接池问题。

此解决方案与内部部署数据库服务器完美配合。 但它不适用于Azure Sql,因为它不支持更改数据库。

提前感谢建议如何维护连接池或更好的方法/最佳实践来处理此类多租户方案。

我之前在使用具有单独数据库的多个租赁方案时已经看到过此问题。 有两个重叠的问题; 每个租户的Web服务器数量以及租户总数。 第一个是更大的问题 – 如果您通过ADO.net连接池缓存数据库连接,那么任何特定客户连接进入与其数据库打开连接的Web服务器的可能性与您的Web服务器数量成反比有。 扩展得越多,当Web服务器代表他们与数据库建立初始连接时,任何给定客户都会注意到每次调用(而不是初始登录)延迟。 对非粘性,高度扩展的Web服务器层进行的每次调用都将越来越不可能找到可以重用的现有开放数据库连接。

第二个问题只是在你的池中有这么多连接,以及这可能会造成内存压力或性能不佳。

您可以通过建立有限数量的数据库应用程序服务器(简单WCF端点)来“解决”第一个问题,这些服务器代表您的Web服务器执行数据库通信。 每个WCF数据库应用程序服务器服务于已知的客户连接池(东部区域转到服务器A,西部区域转到服务器B),这意味着对于任何给定请求,连接池的可能性非常高。 这也允许您单独扩展对数据库的访问以访问HTML呈现Web服务器(数据库是您最关键的性能瓶颈,因此这可能不是一件坏事)。

第二种解决方案是通过NLB路由器使用特定于内容的路由。 这些路由流量基于内容,允许您通过客户分组(西部地区,东部地区等)对您的Web服务器层进行分段,因此每组Web服务器的活动连接数量都少得多,相应增加了获取的可能性一个开放和未使用的连接。

这两个问题通常都是缓存问题,您扩展为完全“不粘”架构的次数越多,任何调用对缓存数据的影响就越小 – 无论是缓存数据库连接还是读取缓存数据。 管理用户连接以允许高速缓存命中的最大可能性对于保持高性能是有用的。

限制每个应用服务器的连接池数量的另一种方法是使用应用程序请求路由(ARR)来划分您的租户并将它们分配给Web层的子集。 这有助于实现更具可扩展性的“pod”架构,其中“pod”是耦合到数据库子集的web / app服务器的小集合。 这里有一篇关于这种方法的好文章: http : //azure.microsoft.com/blog/2013/10/31/application-request-routing-in-csf/

如果要构建多租户数据库应用程序Azure,则还应检出新的Elastic Sc​​ale客户端库,这些库可简化与数据相关的路由并促进跨分片查询和管理操作。 http://azure.microsoft.com/en-us/documentation/articles/sql-database-elastic-scale-documentation-map/