Тайм-аут TinyTDS и блокирует много
У меня относительно большая система, работающая с Rails и TinyTds (адаптер базы данных SQLServer, использующий FreeTds). Проблема в том, что я получаю около 200 писем в день, в которых говорится, что мои запросы истекают или блокируются.
[Exception] application#index (ActionView::Template::Error) "TinyTds::Error: Adaptive Server connection timed out: EXEC sp_executesql
Они всегда случаются на разных действиях.
A ActiveRecord::DeadlockVictim occurred in transportes#importacao:
TinyTds::Error: Transaction (Process ID 276) was deadlocked on lock resources with another process and has been chosen as the deadlock victim. Rerun the transaction.
Я понятия не имею, почему он так много времени истекает и боролся с этими письмами в течение почти 2 месяцев. Я уже пытался обновить версию gem, бинарный файл Linux FreeTds и ничего не помогает.
В настоящее время используется Ruby 1.9.3-p484, Rails 3.2.16 и TinyTds 0.6.2
Кто-нибудь может дать мне некоторое представление о том, как решить эту проблему?
1 ответ
Я предлагаю вам несколько вариантов, которые вы могли бы попробовать..
- По умолчанию компонент Database Engine выбирает в качестве жертвы взаимоблокировки сеанс, в котором выполняется транзакция, для которой откат будет наименее затратным. В качестве альтернативы пользователь может указать приоритет сеансов в ситуации взаимоблокировки, используя инструкцию SET DEADLOCK_PRIORITY. Для параметра DEADLOCK_PRIORITY может быть задано значение LOW, NORMAL или HIGH, или, в качестве альтернативы, может быть установлено любое целочисленное значение в диапазоне (от -10 до 10).
- Настройка времени ожидания блокировки, когда экземпляр ядра СУБД Microsoft SQL Server не может предоставить блокировку транзакции, поскольку другая транзакция уже владеет конфликтующей блокировкой ресурса, первая транзакция блокируется в ожидании снятия существующей блокировки. По умолчанию нет обязательного периода ожидания и нет способа проверить, заблокирован ли ресурс перед его блокировкой, кроме попытки доступа к данным (и, возможно, блокировки на неопределенный срок).
В следующем примере период ожидания блокировки устанавливается равным 1800 миллисекундам.
SET LOCK_TIMEOUT 1800;
GO
- Количество индексов: мы должны определить, улучшат ли дополнительные или меньшие индексы тупик. Дополнительные индексы были бы необходимы, если в большинстве случаев происходит сканирование таблицы. Кроме того, потребуется меньше индексов, если существуют ненужные индексы, которые не используются в плане запросов для каких-либо запросов, и эти ненужные индексы необходимо обновлять во время каждого оператора INSERT, UPDATE и DELETE, что увеличивает время выполнения этих операторов, что также увеличить шансы тупиков.