Не могу понять, на английском читаю, кажется что ничего дополнительного не делает не документированная фича skip locked в oracle 11g.
Объясните, какие различия с этой фичей и без неё.
Ответ
Разница между запросоми с for update, с опцией skip locked и без неё, следующая:
Без этой опции запрос не вернётся, если в выборке есть как минимум одна залоченная строчка. Т.е. он будет ожидать (wait) пoка трансакция не будет завершена в сессии, которая затребовала lock. Если добавить nowait, то он вернётся сразу же с исключением, которое может быть обработано.
ORA-00054: resource busy and acquire with NOWAIT specified or timeout expired
С опцией skip locked он вернётcя сразу же и вернёт только незалоченные строчки или no rows selected, если таковых нет.
И важное отличие для работы с курсорами - курсор с for update залочит все строки попадающие под условие курсора сразу при open, а если добавить skip locked, то только те строки будут залочены, которые были действительно считаны в fetch, что позволяет: ограничить коллличество залоченых строк, или возвращать открытый курсор как результат функции с ещё не залочеными строками.
Не документированной опция skip locked была в 9i и 10g версиях. С 11g она документирована, см. здесь.
В этом ответе подрузумевается row lock, для exclusive table lock см. документацию.
Небольшой пример. В первой сессии:
SQL> select emp_id from emp where emp_id in (1, 2) for update;
EMP_ID
----------
1
2
2 rows selected.
В другой сессии:
SQL> select emp_id from emp where emp_id in (1, 2, 3) for update nowait;
select emp_id from emp where emp_id in (1, 2, 3) for update nowait
*
ERROR at line 1:
ORA-00054: resource busy and acquire with NOWAIT specified or timeout expired
SQL> select emp_id from emp where emp_id in (1, 2, 3) for update skip locked;
EMP_ID
----------
3
1 row selected.
SQL> select emp_id from emp where emp_id in (1, 2, 3) for update;
-- ждёт, пока в первой сессии не будет произведён откат
Комментариев нет:
Отправить комментарий