например. При возникновении взаимоблокировки следующие команды SQL успешно выполняются, даже если им назначена транзакция SQL после отката. Кажется, это вызвано новой неявной транзакцией, созданной на SQL Server.
Кто-то может ожидать, что ADO.NET выдаст исключение, что команды выполняются в транзакции зомби. Однако такое исключение не выбрасывается. (Я думаю, что это ошибка в ASP.NET.) Более того, из-за транзакции зомби финальная Dispose()
молча игнорирует откат.
Есть идеи, как я могу гарантировать, что никто не сможет выполнять команды при неявной транзакции?
Или как проверить, что транзакция зомби? Я обнаружил, что Commit()
и Rollback()
проверяют транзакцию зомби, однако я могу вызвать их для проверки:)
Я также обнаружил, что проверка также выполняется при чтении IsolationLevel, но я не уверен, что будущий оптимизатор не удалит простой вызов transaction.IsolationLevel.ToString();
. Или вы знаете какой-либо другой безопасный способ вызвать геттер (без использования отражения или IL-излучения)?
РЕДАКТИРОВАТЬ: Ремус Русану указал, что эта ситуация обычно не происходит. Да, это правда. Обычно это происходит, когда в коде есть ошибка. В нашем случае в операторе finally была некоторая подпрограмма регистрации, которая пыталась сохранить ошибку в базе данных. Сейчас я пытаюсь найти решение, как обнаружить такие ошибки в будущем. Так как эти ошибки сложно проверить. Если ADO.NET проверит, что предоставленная транзакция - зомби, эта ошибка будет обнаружена гораздо проще. Я нашел две возможности:
- Отключить создание неявных транзакций - я не уверен, возможно ли это.
- Убедитесь, что перед выполнением любых команд будет запущена проверка транзакции зомби.