Может ли запрос с уровнем изоляции READ UNCOMMITTED вызвать блокировку таблиц, к которым он обращается?

Моему приложению требуется пакетная обработка 10 млн строк — результат сложного SQL-запроса, соединяющего таблицы.
Я планирую повторять набор результатов, читая по сотне за итерацию.
Чтобы запустить это на загруженном производстве OLTP. БД и избегайте блокировок, я решил, что буду запрашивать с уровнем изоляции READ UNCOMMITTED.
Уберет ли это запрос с пути любой БД? пишет? избежать блокировок строк/таблиц?

Моя главная проблема заключается в том, что мой запрос блокирует любую другую активность БД, меня гораздо меньше беспокоит обратное.

Дополнительные примечания:
1. Я буду читать исторические данные, поэтому вряд ли встречу незафиксированные данные. Ничего страшного, если я это сделаю.
2. Процесс итерации может занять несколько часов. Соединение с БД останется открытым во время этого процесса.
3. У меня будет максимум два таких одновременных экземпляра пакета.
4. Я могу допустить повторяющиеся строки. (в результате незафиксированного чтения).
5. Целевой БД является DB2, но мне нужно решение, которое подходит и для других поставщиков БД.
6. Поможет ли мне уровень изоляции моментальных снимков очистить память сервера?


person Gili Nachum    schedule 11.11.2013    source источник
comment
Какую СУБД вы используете? Сибас? SQL-сервер? MySQL?   -  person a_horse_with_no_name    schedule 11.11.2013
comment
DB2 (основной), MSSQL, Oracle.   -  person Gili Nachum    schedule 11.11.2013
comment
Oracle никогда не позволяет вам читать незафиксированные данные, и READ UNCOMMITTED не требуется, потому что читатели никогда не блокируют записи, а писатели никогда не блокируют считывателей в Oracle (и в DB2, начиная с 9.7).   -  person a_horse_with_no_name    schedule 12.11.2013
comment
@a_horse_with_no_name, не слишком ли это общее утверждение? разве это не будет зависеть от уровня изоляции читателя и автора?   -  person Gili Nachum    schedule 12.11.2013
comment
Нет, это не слишком общее. Так работает Oracle. На самом деле так же работают и некоторые другие СУБД: Postgres, Firebird, MySQL/InnoDB и даже SQL Server, если они правильно настроены. Он основан на архитектуре MVCC: en.wikipedia.org/wiki/Multiversion_concurrency_control.   -  person a_horse_with_no_name    schedule 12.11.2013


Ответы (3)


Сталкивались ли вы с реальными блокировками при чтении?

Насколько я понимаю, единственная причина, по которой READ UNCOMMITED существовал в стандарте SQL, заключалась в том, чтобы разрешить чтение без блокировки. Так что я не знаю DB2, но бьюсь об заклад, что она не блокирует данные во время чтения в режиме READ UNCOMMITED. Однако большинство современных СУБД вообще не блокируют данные во время чтения (*). Таким образом, READ UNCOMMITED либо недоступен (например, в Oracle), либо автоматически повышается до READ COMMITED (PostgreSQL).

Если вы можете свободно выбирать механизм, проверьте обработку уровня изоляции транзакций DB2 или выберите Oracle/PostgreSQL/другое.

(*) Точнее, они не исключительно блокируют данные. Некоторые общие блокировки могут быть размещены на запрошенных таблицах, поэтому DDL не изменяет их во время чтения.

person Kombajn zbożowy    schedule 11.11.2013
comment
Честно говоря еще не пробовал, проверяю реализуемость решения. Значит, меня беспокоит только DDL? Я полностью согласен с этим. - person Gili Nachum; 12.11.2013

Мой ответ относится к SQL Server.

Чтение зафиксированных релизов блокируется после чтения каждой строки (приблизительно). Блокировка, вероятно, не ваша проблема.

Я рекомендую вам использовать более безопасный READ COMMITTED. Еще лучше использовать изоляцию моментальных снимков. Это устраняет многие проблемы с блокировкой. Есть и недостатки, так что лучше немного почитать об этом.

Меня больше всего беспокоит мой запрос, блокирующий любую другую активность БД.

Изоляция снэпшотов устраняет все проблемы с блокировкой для транзакций только для чтения. Никакой блокировки в любом случае, полная согласованность данных. Имейте в виду, что длительные транзакции могут привести к заполнению TempDB версиями моментальных снимков.

В этом процессе соединение с БД останется открытым.

Это проблема, потому что сбой сети, развертывание приложения или отказоустойчивость зеркального отображения могут убить ваш пакетный процесс.

Имейте в виду, что незафиксированное чтение может привести к тому, что запросы будут спорадически завершаться с ошибкой. Вам нужно повторить логику или терпеть неудачные задания.

person usr    schedule 11.11.2013
comment
Что могло заблокировать мои запросы с READ_COMMITTED? и что бы я заблокировал? Изоляция моментального снимка. При создании моментального снимка с READ_COMMITTED не будет ли он блокировать другие транзакции? Я предполагаю, что это также не поддерживается всеми поставщиками БД? Сбои. Моя пакетная обработка знает, как возобновить работу с того места, где она осталась в последний раз, так что это не проблема. Не знал о спорадическом отказе, почему? определенные крайние случаи БД? - person Gili Nachum; 12.11.2013
comment
Чтение, зафиксированное с помощью SQL Server, обычно не блокирует другие транзакции, потому что все S-блокировки чрезвычайно недолговечны. По стечению обстоятельств он, конечно, может блокировать другие операции записи на очень короткое время. Не могу представить, чтобы это беспокоило вас. Х-блокировки с активацией блокировки другими трансами могут заблокировать считыватель с фиксированным чтением.; Изоляция моментальных снимков SQL Server действительно не блокирует и не блокирует другие. Вы можете удалить всю таблицу, и снимок не будет заблокирован; SQL Server может прервать запрос, если следующая страница, которую он ожидает увидеть с незафиксированным чтением индекса b-дерева, исчезнет. Без замков такое бывает. - person usr; 12.11.2013

В уровне изоляции транзакций сервера sql. Чтение незафиксированных не приводит к блокировке таблицы.

person Amir Keshavarz    schedule 11.11.2013