Reputation: 5223
In the official example here we have the SET TRANSACTION ISOLATION LEVEL
being used in conjunction with an explicitly defined transaction.
My question is, if I execute a query from a SqlCommand, like:
SET TRANSACTION ISOLATION LEVEL READ UNCOMMITTED;
SELECT * from MyTable
would I benefit from the new isolation level I set?
Or do I need to explicitly define a transaction like this?
SET TRANSACTION ISOLATION LEVEL READ UNCOMMITTED;
BEGIN TRANSACTION;
SELECT * from MyTable
COMMIT TRANSACTION;
UPDATE: As per Randy Levy's answer, I will update my query as follows:
SET TRANSACTION ISOLATION LEVEL READ UNCOMMITTED;
SELECT * from MyTable;
SET TRANSACTION ISOLATION LEVEL READ COMMITTED;
This is to overcome possible isolation level leaks when using pooling.
Upvotes: 3
Views: 3791
Reputation: 22655
Yes, you would benefit from the transaction isolation level that you set even if not within an explicit BEGIN TRANSACTION
. When you set the transaction isolation level it is set on a connection level.
From SET TRANSACTION ISOLATION LEVEL (Transact-SQL):
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.
One "gotcha" (issue) that can occur is that the isolation level can leak between different connections when using pooling. If you are explicitly setting an isolation level in one (or some) particular piece(s) of code (but using the default most other places) and also using connection pooling. This can cause strange issues if code expects the default isolation level "A" but obtains a connection that had the isolation level explicitly set to "B".
It seems this issue is now fixed in later versions of SQL Server: SQL Server: Isolation level leaks across pooled connections
Upvotes: 3
Reputation: 32667
Every statement in SQL Server is run in the context of a transaction. When you do something like
select * from [dbo].[foobar];
SQL Server really does:
begin transaction;
select * from [dbo].[foobar];
commit;
So, setting an explicit transaction isolation level does affect transactions. Even the implicit ones that the database engine starts on your behalf!
Upvotes: 1
Reputation: 29207
The first one
SET TRANSACTION ISOLATION LEVEL READ UNCOMMITTED;
SELECT * from MyTable
will work. The transaction level you set applies to each subsequent transaction, and your SELECT statement is its own implicit transaction.
You would only need to explicitly start a transaction if you needed to ensure some degree of consistency throughout multiple reads. For example if you use SERIALIZABLE then you could wrap multiple SELECTs in a transaction and ensure that the underlying data isn't modified while you're reading it.
Upvotes: 2