В моем текущем приложении я выполняю обновление путем вызова команды T-SQL Update. Проблема состоит в том, когда та же запись заблокирована другими пользователями в то время.
В приложении.NET будет ожидать приложение до тайм-аута SQL Server затем оно бросит тайм-аут SqlException.
Действительно ли возможно выполнить проверку сначала, заблокирована ли конкретная запись другим процессом вместо того, чтобы ловить исключение?
Нет, не совсем.
Стандартный способ - использовать try / catch
и обработать SqlException
Number 1205
(жертва взаимоблокировки) и повторить запрос:
try
{
// do stuff...
}
catch (SqlException sqlEx)
{
switch (sqlEx.Number)
{
case -2: // Client Timeout
case 701: // Out of Memory
case 1204: // Lock Issue
case 1205: // >>> Deadlock Victim
// handle deadlock
break;
case 1222: // Lock Request Timeout
case 2627: // Primary Key Violation
case 8645: // Timeout waiting for memory resource
case 8651: // Low memory condition
...
}
}
[Примечание: операторы break не добавлены для компактности
Также обратите внимание на , многие проблемы с блокировкой можно устранить, предоставив соответствующие индексы покрытия.
Вы можете использовать отдельное соединение с очень коротким таймаутом, чтобы попытаться заблокировать запись, обновив какое-либо поле, но это все равно не даст вам 100% надежности .
если у вас действительно есть ситуация, когда несколько пользователей редактируют одни и те же записи, вам следует изучить методы оптимистической блокировки.
Также убедитесь, что вы вообще не разрешаете пользователям блокировать записи - используйте отключенный режим для любых обновлений. Другими словами, блокировка будет происходить только на короткое время обновления (<100 мс)