Я намагаюся зрозуміти / навчитися відслідковувати деталі заблокованого сеансу.
Тому я створив таку настройку:
create table foo (id integer not null primary key, some_data varchar(20));
insert into foo values (1, 'foo');
commit;
Тепер я підключаюся до бази даних двічі від двох різних клієнтів.
Проблеми першого сеансу:
begin transaction
update foo set some_data = 'update'
where id = 1;
Я явно не беру на себе зобов’язання, щоб зберегти замки.
На другому сеансі я видаю ту саму заяву, і звичайно, що один чекає через блокування. Тепер я намагаюся використовувати різні запити, що плавають навколо, щоб побачити, що сеанс 2 чекає foo
таблиці.
sp_who2
показує наступне (я видалив кілька стовпців, щоб відобразити лише важливу інформацію):
SPID | Статус | BlkBy | DBName | Команда | SPID | ЗАПИТАННЯ ----- + -------------- + ------- + ---------- + ---------- -------- + ------ + ---------- 52 | спить | . | foodb | ЗАЧЕКАЄМО КОМАНДА | 52 | 0 53 | спить | . | foodb | ЗАЧЕКАЄМО КОМАНДА | 53 | 0 54 | СУСПАННІ | 52 | foodb | ОНОВЛЕННЯ | 54 | 0 56 | РАБОНА | . | foodb | ВИБІРТЬ У ВІД | 56 | 0
Очікується, що сеанс 54 заблокований несвідомими змінами з сеансу 52.
Це sys.dm_os_waiting_tasks
також показує запит . Заява:
select session_id, wait_type, resource_address, resource_description
from sys.dm_os_waiting_tasks
where blocking_session_id is not null;
повертає:
session_id | wait_type | address_address | resource_description ----------- + ----------- + -------------------- + ----- -------------------------------------------------- -------------------------- 54 | LCK_M_X | 0x000000002a35cd40 | keylock hobtid = 72057594046054400 dbid = 6 id = lock4ed1dd780 режим = X пов'язанийObjectId = 72057594046054400
Знову це очікується.
Моя проблема полягає в тому, що я не можу зрозуміти, як знайти власне ім'я об'єкта, якого чекає сеанс 54.
Я знайшов декілька запитів, які приєднуються sys.dm_tran_locks
і sys.dm_os_waiting_tasks
подібні до цього:
SELECT ....
FROM sys.dm_tran_locks AS l
JOIN sys.dm_os_waiting_tasks AS wt ON wt.resource_address = l.lock_owner_address
Але в моєму вище тестовому сценарії це приєднання нічого не повертає. Отже, або це приєднання неправильне, або dm_tran_locks
насправді не містить інформації, яку я шукаю.
Тому я шукаю запит, який повертає щось на зразок:
" сесія 54 чекає блокування в таблиціfoo
".
Довідкова інформація:
Справжня життєва проблема, яку я намагаюся вирішити, є дещо складнішою, але зводиться до питання "за яким столом чекає сесія 54". Проблема, про яку йдеться, передбачає велику збережену процедуру, яка оновлює декілька таблиць, а також виберіть з точки зору, що отримує доступ до деяких із цих таблиць. Оператор select
блокується, навіть якщо у нас є ізоляція знімків та ввімкнено читання зроблених знімків. З'ясування, чому вибір заблокований (що, на мою думку, не вдасться, якщо включена ізоляція знімків), буде наступним кроком.
В якості першого кроку я хотів би дізнатися, на те , що очікує , що сесія.