Голанг sql.Количество ожиданий БД больше 0, даже если в пуле достаточно незанятых подключений

# #mysql #go

Вопрос:

Я смотрю на статистику базы данных веб-приложения в Голанге. Метрики экспортируются в prometheus каждые 10 секунд с помощью sqlstats.

В приложении MaxOpenConns установлено значение 100 и MaxIdleConns установлено значение 50. И когда я смотрю на показатели, я замечаю, что количество открытых соединений стабильно около 50. Это ожидается, а это значит, что мы сохраняем 50 незанятых соединений. Однако число InUse подключений колеблется от 0 до 5 и большую часть времени равно 0. Это странно для меня, потому что существует постоянный приток трафика, и я не ожидаю, что количество InUse подключений будет равно 0.

Кроме того, я замечаю WaitCount , MaxIdleClosed что они довольно большие. WaitCount означает, что не осталось незанятых соединений и sql.БД не может открыть больше соединений из-за MaxOpenConns ограничения. Но, судя по приведенной выше статистике, для sql, похоже, более чем достаточно места.БД для создания дополнительных подключений ( OpenConnections см. ниже MaxOpenConnections ). Большое количество MaxIdleClosed также указывает на то, что sql.DB создает дополнительные соединения, даже если имеется достаточно незанятых соединений.

В то же время я наблюдаю некоторые driver: bad connection ошибки в приложении, и мы используем MySQL.

Почему приложение пытается открыть больше подключений, когда вокруг достаточно незанятых подключений, и как мне настроить параметры базы данных, чтобы уменьшить проблему?

Комментарии:

1. В приведенном выше вопросе вы упомянули active о связях. Но в DBStats нем нет параметра с именем в качестве active соединений. Было бы легко понять, если бы вы могли описать проблему, используя термины, используемые в пакете, который вы используете. Например, под active связями вы подразумеваете InUse связи??

2. @SaiRaviTejaK правильно, обновит вопрос

Ответ №1:

Однако число используемых соединений колеблется от 0 до 5 и большую часть времени равно 0. Это странно для меня, потому что существует постоянный приток трафика, и я не ожидаю, что количество неиспользуемых соединений будет равно 0.

В этом нет ничего странного. Количество неиспользуемых соединений растет как на дрожжах. Поскольку вы получаете статистику только каждые 10 секунд, вы просто не видите всплеска.

Почему приложение пытается открыть больше соединений, когда вокруг достаточно незанятых соединений,

Видишь https://github.com/go-sql-driver/mysql#important-settings

«db.SetMaxIdleConns() рекомендуется установить равным (или больше) db.SetMaxOpenConns(). Когда он меньше, чем SetMaxOpenConns(), соединения могут открываться и закрываться очень часто, чем вы ожидаете».

и как я должен настроить параметры базы данных, чтобы уменьшить проблему?

Следуйте рекомендациям go-sql-драйвера/mysql README. Используйте db.SetConnMaxLifetime() и установите db.SetMaxIdleConns() то же значение db.SetMaxOpenConns() .

 db.SetMaxOpenConns(100)
db.SetMaxIdleConns(100)
db.SetConnMaxLifetime(time.Minute * 3)