gpt4 book ai didi

postgresql - Azure Function 创建了太多与 PostgreSQL 的连接

转载 作者:行者123 更新时间:2023-11-29 11:18:00 28 4
gpt4 key购买 nike

我有一个 Azure Durable Function,它与同样托管在 Azure 中的 PostgreSQL 数据库交互。

PostgreSQL数据库的连接限制为50,此外,我的连接字符串将连接池大小限制为40,为 super 用户/管理员连接留出空间。

尽管如此,在某些负载下我收到错误

53300: remaining connection slots are reserved for non-replication superuser connections

This documentation from Microsoft似乎相关,但我似乎无法制作静态客户端,并且,正如它提到的,

because you can still run out of connections, you should optimize connections to the database.

我有这个方法

private IDbConnection GetConnection()
{
return new NpgsqlConnection(Environment.GetEnvironmentVariable("PostgresConnectionString"));
}

当我想与 PostgreSQL 交互时,我确实喜欢这样

using (var connection = GetConnection())
{
connection.Open();
return await connection.QuerySingleAsync<int>(settings.Query().Insert, settings);
}

因此,我正在创建(并处置)大量 NpgsqlConnection 对象,但根据 this ,这应该没问题,因为连接池是在幕后处理的。但 Azure Functions 的某些方面可能使这种想法无效。

我注意到我最终得到了很多空闲连接(来自 pgAdmin): pgAdmin connection graph基于此,我尝试摆弄 Npgsql connection parameters例如Connection Idle LifetimeTimeoutPooling,但连接过多的问题似乎在某种程度上仍然存在。此外,我尝试限制并发协调器和事件函数的数量(请参阅 this doc ),但这似乎部分违背了 Azure Functions 可扩展的目的。它确实有帮助 - 我得到的连接数错误较少)。据推测,如果我继续用较低的数字测试它,我什至可能会消除它,但同样,这似乎违背了要点,并且可能还有另一种解决方案。

如何在不耗尽连接的情况下将 PostgreSQL 与 Azure Functions 结合使用?

最佳答案

我没有好的解决方案,但我想我已经解释了为什么会发生这种情况。

为什么 Azure Function App 会超出连接数?

即使您将池大小指定为 40,也仅在函数应用的一个实例上遵循该限制。请注意,函数应用程序可以根据负载进行扩展。它可以在同一功能应用程序实例中同时处理多个请求,此外它还可以创建应用程序的新实例。同一实例中的并发请求将遵循池大小设置。但在多个实例的情况下,每个实例最终使用的池大小为 40。

即使持久函数中的并发限制也无法解决此问题,因为它们仅在单个实例内进行限制,而不是跨实例。

如何在不耗尽连接的情况下将 PostgreSQL 与 Azure Functions 结合使用?

不幸的是,函数应用程序不提供执行此操作的 native 方法。请注意,连接池大小不是由函数运行时管理的,而是由 npgsql 的库代码管理的。在不同实例上运行的库代码无法相互通信。

请注意,这是使用共享资源的经典问题。在本例中,您有 50 个这样的资源。支持更多消费者的最有效方法是减少每个消费者使用资源的时间。 大幅减少连接空闲生命周期可能是最有效的方法。增加Timeout确实有助于减少错误(并且是一个不错的选择),但它不会增加吞吐量。它只是平滑负载。减少最大池大小也不错。

将其视为共享资源上的锁。您希望锁定的时间最短。当打开一个连接时,它会锁定总共 50 个连接之一。一般来说,SQL 库会进行池化,并保持连接打开以节省每个新连接所涉及的初始设置时间。但是,如果这限制了并发性,那么最好尽快终止空闲连接。在应用程序的单个实例中,当达到最大池大小时,库会自动执行此操作。但在多个实例中,它无法终止另一个实例的连接。

需要注意的一件事是,减少最大池大小并不一定会限制应用的并发性。在大多数情况下,它只是减少空闲连接的数量 - 代价是 - 当稍后需要建立新连接时支付初始设置时间。

更新

WEBSITE_MAX_DYNAMIC_APPLICATION_SCALE_OUT可能有用。您可以将其设置为 5,并将池大小设置为 8 或类似值。如果减少最大池大小连接空闲生命周期没有帮助,我会采用这种方式。

关于postgresql - Azure Function 创建了太多与 PostgreSQL 的连接,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/56977209/

28 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com