Lokala transaktioner
Transaktioner i ADO.NET används när du vill binda samman flera uppgifter så att de körs som en enda arbetsenhet. Anta till exempel att ett program utför två uppgifter. Först uppdateras en tabell med orderinformation. För det andra uppdateras en tabell som innehåller inventeringsinformation och debiterar de beställda objekten. Om någon av aktiviteterna misslyckas återställs båda uppdateringarna.
Fastställa transaktionstyp
En transaktion anses vara en lokal transaktion när det är en enfastransaktion och hanteras direkt av databasen. En transaktion anses vara en distribuerad transaktion när den samordnas av en transaktionsövervakare och använder felsäkra mekanismer (till exempel tvåfasincheckning) för transaktionsmatchning.
Var och en av .NET Framework-dataprovidrar har ett eget Transaction
objekt för att utföra lokala transaktioner. Om du kräver att en transaktion utförs i en SQL Server-databas väljer du en System.Data.SqlClient transaktion. Använd providern för System.Data.OracleClient en Oracle-transaktion. Dessutom finns det en DbTransaction klass som är tillgänglig för att skriva provideroberoende kod som kräver transaktioner.
Kommentar
Transaktioner är mest effektiva när de utförs på servern. Om du arbetar med en SQL Server-databas som använder explicita transaktioner i stor utsträckning kan du skriva dem som lagrade procedurer med transact-SQL BEGIN TRANSACTION-instruktionen.
Utföra en transaktion med en enda Anslut ion
I ADO.NET kontrollerar du transaktioner med Connection
objektet. Du kan initiera en lokal transaktion med BeginTransaction
metoden . När du har påbörjat en transaktion kan du registrera ett kommando i transaktionen Transaction
med egenskapen för ett Command
objekt. Du kan sedan checka in eller återställa ändringar som gjorts i datakällan baserat på lyckade eller misslyckade komponenter i transaktionen.
Kommentar
Metoden EnlistDistributedTransaction
ska inte användas för en lokal transaktion.
Transaktionens omfattning är begränsad till anslutningen. I följande exempel utförs en explicit transaktion som består av två separata kommandon i try
blocket. Kommandona kör INSERT-instruktioner mot tabellen Production.ScrapReason i AdventureWorks SQL Server-exempeldatabasen, som checkas in om inga undantag utlöses. Koden i catch
blocket återställer transaktionen om ett undantag utlöses. Om transaktionen avbryts eller om anslutningen stängs innan transaktionen har slutförts återställs den automatiskt.
Exempel
Följ de här stegen för att utföra en transaktion.
BeginTransaction Anropa -metoden för SqlConnection objektet för att markera transaktionens början. Metoden BeginTransaction returnerar en referens till transaktionen. Den här referensen tilldelas till de SqlCommand objekt som är registrerade i transaktionen.
Transaction
Tilldela objektet till egenskapen Transaction för den SqlCommand som ska köras. Om ett kommando körs på en anslutning med en aktiv transaktion ochTransaction
objektet inte har tilldelats egenskapenCommand
förTransaction
objektet genereras ett undantag.Kör de kommandon som krävs.
Commit Anropa -metoden för SqlTransaction objektet för att slutföra transaktionen eller anropa Rollback metoden för att avsluta transaktionen. Om anslutningen stängs eller tas bort innan metoderna Commit eller Rollback har körts återställs transaktionen.
I följande kodexempel visas transaktionslogik med ADO.NET med Microsoft SQL Server.
using (SqlConnection connection = new(connectionString))
{
connection.Open();
// Start a local transaction.
SqlTransaction sqlTran = connection.BeginTransaction();
// Enlist a command in the current transaction.
SqlCommand command = connection.CreateCommand();
command.Transaction = sqlTran;
try
{
// Execute two separate commands.
command.CommandText =
"INSERT INTO Production.ScrapReason(Name) VALUES('Wrong size')";
command.ExecuteNonQuery();
command.CommandText =
"INSERT INTO Production.ScrapReason(Name) VALUES('Wrong color')";
command.ExecuteNonQuery();
// Commit the transaction.
sqlTran.Commit();
Console.WriteLine("Both records were written to database.");
}
catch (Exception ex)
{
// Handle the exception if the transaction fails to commit.
Console.WriteLine(ex.Message);
try
{
// Attempt to roll back the transaction.
sqlTran.Rollback();
}
catch (Exception exRollback)
{
// Throws an InvalidOperationException if the connection
// is closed or the transaction has already been rolled
// back on the server.
Console.WriteLine(exRollback.Message);
}
}
}
Using connection As New SqlConnection(connectionString)
connection.Open()
' Start a local transaction.
Dim sqlTran As SqlTransaction = connection.BeginTransaction()
' Enlist a command in the current transaction.
Dim command As SqlCommand = connection.CreateCommand()
command.Transaction = sqlTran
Try
' Execute two separate commands.
command.CommandText = _
"INSERT INTO Production.ScrapReason(Name) VALUES('Wrong size')"
command.ExecuteNonQuery()
command.CommandText = _
"INSERT INTO Production.ScrapReason(Name) VALUES('Wrong color')"
command.ExecuteNonQuery()
' Commit the transaction
sqlTran.Commit()
Console.WriteLine("Both records were written to database.")
Catch ex As Exception
' Handle the exception if the transaction fails to commit.
Console.WriteLine(ex.Message)
Try
' Attempt to roll back the transaction.
sqlTran.Rollback()
Catch exRollback As Exception
' Throws an InvalidOperationException if the connection
' is closed or the transaction has already been rolled
' back on the server.
Console.WriteLine(exRollback.Message)
End Try
End Try
End Using