4

Я использую следующий формат для внесения изменений в мой db с помощью linq.LINQ + TransactionScope не изменит уровень изоляции в SQL Server Profiler

Begin Transaction (Scope Serialized, Required) 
    Check Business Rule 1...N 
    MyDataContext.SubmitChanges() 
    Save Changes Done In Previous Query To Log File 
End Transaction Scope 

Но в профилировщике SQL Server я вижу следующую строку в Connection: Start.

set transaction isolation level read committed 

Я прошел через это (http://social.msdn.microsoft.com/Forums/en-US/adodotnetentityframework/thread/93a45026-0425-4d49-a4ac-1b882e90e6d5) и думал, что у меня был ответ;

До тех пор пока я не увидел это (https://connect.microsoft.com/VisualStudio/feedback/details/565441/transactionscope-linq-to-sql?wa=wsignin1.0) в Microsoft Connect.

Может кто-нибудь, пожалуйста, скажите, действительно ли мой код выполняется в режиме Serialized Isolation Level, или он является действительным только при чтении?

+0

Я бы склонен верить тому, что вы видите в Профилире ... –

+0

Но также было сказано в одном из сообщений, что профайлер показывает только уровень изоляции при запуске соединения: S –

+0

Если вы не видите никаких других операторы, относящиеся к уровню изоляции в профилировщике, то это уровень изоляции. –

ответ

7

Это зависит от того, как вы создали транзакцию.

Если вы выполнили встроенный SQL для его начала (EG BEGIN TRAN), L2S не будет знать о транзакции и разворачивает новую вложенную в READ COMMITTED.

Однако, если вы использовали System.Transaction или имеете транзакцию, установленную на DataContext, SubmitChanges будут участвовать в этой транзакции.

Вы можете увидеть эти транзакции, начав и остановившись в профилировщике, если вы выберете классы событий и TM: Commit Tran.

Примечание: ADO.Net не выпускает BEGIN TRAN и не выпускает SET TRANSACTION ISOLATION партиями, это делается на более низком уровне.

Если вы правильно указали , создайте триггер на таблице, который вставляет текущий уровень изоляции в таблицу протоколирования и проверяет его.

Вы можете забрать свой текущий уровень изоляции, выполнив:

SELECT CASE transaction_isolation_level 
WHEN 0 THEN 'Unspecified' 
WHEN 1 THEN 'Read Uncommitted' 
WHEN 2 THEN 'Read Committed' 
WHEN 3 THEN 'Repeatable Read' 
WHEN 4 THEN 'Serializable' 
WHEN 5 THEN 'Snapshot' END AS TRANSACTION_ISOLATION_LEVEL 
FROM sys.dm_exec_sessions 
where session_id = @@SPID 
+0

Я начинаю свою транзакцию, такую ​​как Begin Transaction (Scope Serialized, Required), как показано в моем сообщении, по любой причине, почему она не показывает уровень изоляции в профилировщике сервера? См. Ссылки, которые я опубликовал. –

1

Я думаю, вы создали DataContext, затем использовали TransactionScope. Вы должны открыть соединение внутри TransactionScope для того, чтобы оно было завербовано.

+0

Нет. Существует свойство, указывающее контексту использование любой существующей транзакции (или требующей новой). Это совсем другая проблема. –

1

От http://entityframework.codeplex.com/workitem/1712

TransactionScope использует удаленный API вызовы, а не SQL команд для выполнения транзакций в SQL Server. Эти вызовы API не включены в стандартную трассировку в SQL Profiler.

Вы можете включить их, перейдя на страницу «Выбор события», нажав на флажок «Показать все события» и выбрав все события из категории «Транзакции». Это позволит вам увидеть, когда на самом деле происходят такие события, как «ТМ: начало переходов», «SQLTransaction» и «TM: Begin Tran Completed».

Вы также можете проверить столбец TransactionID для событий TSQL на странице «Выбор события», чтобы увидеть, к какой транзакции выполняется каждая выполняемая SQL-партия.

К сожалению, я не знаю прямого способа проверить эффективный уровень изоляции, при котором каждая команда выполняется в SQL Profiler. Но есть косвенный путь ...

Когда соединение открыто, вы увидите событие «Аудиторский вход» в трассировке. Во многих случаях это событие будет содержать уровень изоляции. Теперь «Аудиторский вход» происходит до того, как будет установлен фактический уровень изоляции, поэтому уровень изолированного сообщения не будет точно отражать уровень изоляции транзакции, которая вот-вот начнется. Вот несколько советов о том, как их интерпретировать: Когда открытие соединения фактически попадает в новое соединение, оно всегда будет сообщать уровень изоляции транзакции по умолчанию, например. вы увидите, что «уровень изоляции транзакций не читается» (как я уже сказал, это не связано с эффективным уровнем изоляции вашей транзакции, поскольку тот будет установлен в более поздней точке) После того, как соединение было открыто, а затем возвращено в пул соединений (т. е. закрыт), последующие подключения будут фактически повторно использовать существующее соединение из пула. В этом случае «Аудиторский вход» будет сообщать об уровне изоляции, который был установлен, когда соединение было возвращено в пул в последний раз. Это может помочь вам увидеть уровень изоляции, который был использован после факта. . в вашем фрагменте кода соединение открыто в последний раз для отката транзакции (потому что вы не отметили транзакцию как заполненную явно). В этом событии «Аудиторский вход» вы должны увидеть уровень изоляции, который был эффективен, когда соединение было ранее использовано для выполнения запроса, представленное строкой «уровень изоляции транзакции без чтения».