Проблема с производительностью при обновлении в postgres

#sql #node.js #database #postgresql #typeorm

#sql #node.js #База данных #postgresql #typeorm

Вопрос:

У меня есть довольно простое update утверждение в моем приложении в одном из API.

 UPDATE "table" SET "column" = "column"   1 WHERE "id" = $1
  

Проблема в том, что когда этот API подвергается внезапной загрузке, он начинает сбоить. ЦП БД не увеличивается, увеличивается только количество активных сеансов. При проверке RDS performance insights это то, что я вижу. введите описание изображения здесь

Количество обновлений этой таблицы не превышает 300. Я не думаю, что postgres должен вести себя таким образом при таком малом количестве обновлений (время ожидания). Было бы полезно, если бы у меня были предложения, что здесь может быть не так? Я понимаю, что означает ожидание в кортеже и transactionid, но как я могу уменьшить эти ожидания?

Спасибо

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

1. «Количество обновлений этой таблицы не превышает 300» Доказательства, которые вы показываете, свидетельствуют об обратном.

2. Я думаю, вы можете получить лучшие ответы на dba.stackexchange.com .

Ответ №1:

Проблема очевидна: все эти сеансы ожидают блокировки строки. Если все эти сеансы выполняют оператор, который вы цитируете, с одним и тем же id (или только с небольшим количеством разных id s), то они блокируют друг друга.

Поскольку сеансы, похоже, не выполняют никакой работы (если я правильно прочитал график, все они ждут), я бы сказал, что проблема в том, что ваши транзакции занимают слишком много времени. PostgreSQL удерживает блокировку строки, как и все другие пользовательские блокировки, до завершения транзакции, поэтому наличие этого UPDATE в вашей рабочей нагрузке эффективно сериализует обработку.

Вы могли бы улучшить ситуацию, выполнив UPDATE в самом конце транзакции, чтобы блокировка не удерживалась в течение длительного времени. Кроме того, вам следует значительно уменьшить размер пула соединений. Я не думаю, что ваша база данных может обрабатывать 1000 активных подключений.

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

1. Упс. Я не знаю, как я это пропустил. Спасибо, что указали на это @Laurenz. Переместил обновление в конце транзакции. Я собираюсь наблюдать за этим в течение нескольких дней, поскольку это происходит один или два раза в пару недель при большой нагрузке.

Ответ №2:

Уменьшите максимальное количество параллельных HTTP-запросов, которые принимает ваш веб-сервер (при условии HTTP (ов)), чтобы не перегружать базу данных. Это приведет к тому, что запросы API к вашей службе будут помещены в очередь в ожидании TCP-соединения. Это приведет к повышению производительности, а не к ухудшению во время пиковых нагрузок.