Sidekiq 在 AWS RDS 上返回“ActiveRecord::ConnectionTimeoutError:无法在 5.000 秒(等待 5.000 秒)内获得数据库连接”

use*_*621 2 ruby mysql activerecord connection-pooling ruby-on-rails

我正在使用 Sidekiq 在 AWS 服务器上创建 PDF 文档,以便在后台处理此作业。

在创建 PDF 文件的过程中,[Rails] 应用程序正在汇集数据库以检查是否创建了 PDF 文件(间隔:2 秒)。

今天早上我在 Sidekiq 端收到了这个错误信息:

ActiveRecord::ConnectionTimeoutError: could not obtain a database connection within 5.000 seconds (waited 5.000 seconds)
Run Code Online (Sandbox Code Playgroud)

我正在使用带有 MySQL 的 Amazon RDS。

作为临时解决方案,我将pool参数从10增加到30in database.yml,但是我意识到这只是一个临时补丁。

如何正确修复?

谢谢

Bor*_*aMa 5

我认为您的解决方案实际上是正确的。 ActiveRecord::ConnectionPool是基于线程的,即它试图为每个想要使用数据库的线程获取一个单独的连接。如果有更多线程想要访问数据库,则连接池的总大小(使用 中的pool选项配置database.yml),ConnectionPool如果来自某个其他线程的连接被释放,默认情况下会尝试等待最多 5 秒。在这 5 秒超时后,将ActiveRecord::ConnectionTimeoutError引发异常。

现在,Sidekiq默认使用25 个工作线程。因此,在更高的负载下,完全有可能有多达 25 个作业(线程)同时尝试访问数据库。如果您pool设置为 10,则多余的工作人员必须等待其他工作人员完成,并且可能某些线程必须等待太长时间。

所以,无论是连接池的大小扩大到至少一个高一点的值,则25(sidekiq工人的数量),就像你一样,或者运行sidekiq通过像运行它用更少的工人sidekiq -c 5。最后,始终确保在 MySQL 端允许足够的传入连接(默认情况下超过 100)。