Рассмотрим следующий SQL:
BEGIN TRAN
SET TRANSACTION ISOLATION LEVEL READ COMMITTED
INSERT Bands
( Name )
SELECT 'Depeche Mode'
UNION
SELECT 'Arcade Fire'
-- I've indented the inner transaction to make it clearer.
BEGIN TRAN
SET TRANSACTION ISOLATION LEVEL READ UNCOMMITTED
SELECT *
FROM Bands
COMMIT
-- What is the isolation level right here?
UPDATE Bands
SET Name = 'Modest Mouse'
WHERE Name = 'Oddest House'
COMMIT
В общем, мы запускаем транзакцию и устанавливаем ее уровень изоляции READ COMMITTED. Затем мы выполняем произвольный SQL и запускаем другую вложенную транзакцию. В этой транзакции мы меняем уровень изоляции на READ UNCOMMITTED. Затем мы фиксируем эту транзакцию и возвращаемся к другой.
Теперь я предполагаю, что после внутренней фиксации уровень изоляции возвращается к READ COMMITTED. Это верно?





Я не думаю, что это правильно.
См. Примечания здесь: Установить транзакцию
Only one of the isolation level options can be set at a time, and it remains set for that connection until it is explicitly changed.
Вы [Боб Пробст] правы. Интересно, что согласно документация вы связали:
If you issue SET TRANSACTION ISOLATION LEVEL in a stored procedure or trigger, when the object returns control the isolation level is reset to the level in effect when the object was invoked. For example, if you set REPEATABLE READ in a batch, and the batch then calls a stored procedure that sets the isolation level to SERIALIZABLE, the isolation level setting reverts to REPEATABLE READ when the stored procedure returns control to the batch.
Итак, суть в том, что SET TRANSACTION ISOLATION LEVEL имеет родство процедуры, а не привязка транзакции (как я думал).
Потрясающий!
Этот «ответ» должен был быть комментарием. Но дай мне передохнуть. Это был 2008 год. :)
Ну это отстой, лол! Мой API базы данных C# имеет тенденцию принимать открытые объекты соединения, поэтому я могу вызывать несколько функций, не открывая каждый раз новое соединение. Это отсутствие «сродства транзакции» означает, что если я вызываю один метод API базы данных из другого, и оба используют транзакцию, вложенная транзакция может изменить уровень изоляции транзакции транзакции вызывающей стороны. Определенно отстой. ВОЗМОЖНОЕ РЕШЕНИЕ ... для любого метода C#, который использует транзакцию, имитируйте процедурное сходство для транзакций C# с кодом C#, сохраняя уровень изоляции (dbcc useroptions) и восстанавливая его перед возвратом!