Freigeben über


Verwenden von 'System.Transactions'

Gilt für: SQL Server

Der System.Transactions-Namespace stellt ein Transaktionsframework bereit, das vollständig in ADO.NET- und SQL Server Common Language Runtime (CLR)-Integration integriert ist. Die System.Transactions.TransactionScope -Klasse bewirkt, dass ein Codeblock transaktional wird, indem sie Verbindungen implizit in einer verteilten Transaktion einträgt. Sie müssen am Ende des Codeblocks, der durch Complete markiert wird, die TransactionScope-Methode aufrufen. Die Dispose -Methode wird aufgerufen, wenn die Programmausführung einen Codeblock verlässt, was dazu führt, dass die Transaktion nicht fortgeführt wird, wenn die Complete -Methode nicht aufgerufen wird. Wenn eine Ausnahme ausgelöst wurde, die dazu führt, dass der Code den Bereich verlässt, wird die Transaktion als nicht fortgeführt betrachtet.

Wir empfehlen die Verwendung eines using -Blocks um sicherzustellen, dass die Dispose -Methode für das TransactionScope -Objekt aufgerufen wird, wenn der using -Block verlassen wird. Wird für ausstehende Transaktionen kein Commit oder Rollback ausgeführt, wird die Leistung unter Umständen stark beeinträchtigt, da der Timeout für TransactionScope standardmäßig eine Minute beträgt. Wenn Sie keine using -Anweisung verwenden, müssen Sie alle Arbeiten in einem Try -Block ausführen und die Dispose -Methode im Finally -Block explizit aufrufen.

Wenn innerhalb von TransactionScopeeine Ausnahme auftritt, wird die Transaktion als inkonsistent markiert und aufgegeben. Es wird ein Rollback für die Transaktion ausgeführt, wenn TransactionScope verworfen wird. Wenn keine Ausnahme auftritt, wird für teilnehmende Transaktionen ein Commit ausgeführt.

TransactionScope sollte nur verwendet werden, wenn auf lokale Datenquellen und Remotedatenquellen oder externe Ressourcen-Manager zugegriffen wird. Der Grund dafür ist, dass die TransactionScope -Klasse immer zur Höherstufung von Transaktionen führt, selbst dann, wenn sie nur innerhalb einer Kontextverbindung verwendet wird.

Hinweis

Die TransactionScope -Klasse erstellt System.Transactions.Transaction.IsolationLevel standardmäßig mit dem Wert Serializable . Je nach Ihrer Anwendung kann es vorteilhaft sein, die Isolationsstufe herabzusetzen, um ein hohes Konfliktpotenzial in der Anwendung zu vermeiden.

Hinweis

Es empfiehlt sich, nur Updates, Einfügungen und Löschungen innerhalb verteilter Transaktionen für Remoteserver auszuführen, da sie erhebliche Datenbankressourcen in Anspruch nehmen. Wenn der Vorgang auf dem lokalen Server ausgeführt werden soll, ist keine verteilte Transaktion notwendig, sondern es reicht eine lokale Transaktion aus. SELECT-Anweisungen sperren unter Umständen Datenbankressourcen, ohne dass dies erforderlich ist. Und in einigen Szenarien ist die Verwendung von Auswahlen möglicherweise notwendig. Jeder Arbeitsschritt, der nicht die Datenbank betrifft, sollte außerhalb des Transaktionsbereichs durchgeführt werden, sofern keine anderen Ressourcen-Manager von der Transaktion betroffen sind. Wenngleich eine Ausnahme innerhalb des Transaktionsbereichs ein Transaktionscommit verhindert, verfügt die TransactionScope -Klasse nicht über die Möglichkeit, außerhalb des Bereichs der Transaktion selbst ein Rollback von Änderungen auszuführen, die Ihr Code vorgenommen hat. Wenn Sie bestimmte Vorgänge beim Rollback der Transaktion ausführen möchten, müssen Sie eine eigene Implementierung der System.Transactions.IEnlistmentNotification -Schnittstelle schreiben und eine explizite Eintragung in die Transaktion vornehmen.

Beispiel

Um mit System.Transactionszu arbeiten, müssen Sie über einen Verweis auf die Datei System.Transactions.dll verfügen.

Der folgende Code veranschaulicht, wie eine Transaktion erstellt wird, die für zwei verschiedene Instanzen von SQL Server heraufgestuft werden kann. Diese Instanzen werden durch zwei verschiedene System.Data.SqlClient.SqlConnection -Objekte dargestellt, die von einem TransactionScope -Block umschlossen werden. Der Code erstellt den TransactionScope -Block mit einer using -Anweisung und öffnet die erste Verbindung, wodurch sie automatisch im TransactionScopeeingetragen wird. Die Transaktion wird anfänglich als einfache Transaktion, nicht als vollständig verteilte Transaktion, eingetragen. Der Code geht von der Existenz bedingter Logik aus (welche der Kürze halber weggelassen wurde). Er öffnet die zweite Verbindung nur, wenn es nötig ist, und trägt sie dann im TransactionScopeein. Wenn die Verbindung geöffnet wird, wird die Transaktion automatisch auf eine vollständig verteilte Transaktion hochgestuft. Der Code ruft dann TransactionScope.Completeauf, was zur Ausführung eines Commits für die Transaktion führt. Der Code gibt die beiden Verbindungen beim Beenden der using -Anweisungen für die Verbindungen frei. Die TransactionScope.Dispose -Methode für TransactionScope wird am Ende des using -Blocks für TransactionScopeautomatisch aufgerufen. Wenn an einem Punkt im TransactionScope -Block eine Ausnahme aufgetreten ist, wird Complete nicht aufgerufen, und für die verteilte Transaktion wird ein Rollback ausgeführt, sobald der TransactionScope gelöscht wird.

Visual Basic

Using transScope As New TransactionScope()  
    Using connection1 As New SqlConnection(connectString1)  
        ' Opening connection1 automatically enlists it in the   
        ' TransactionScope as a lightweight transaction.  
        connection1.Open()  
  
        ' Do work in the first connection.  
  
        ' Assumes conditional logic in place where the second  
        ' connection will only be opened as needed.  
        Using connection2 As New SqlConnection(connectString2)  
            ' Open the second connection, which enlists the   
            ' second connection and promotes the transaction to  
            ' a full distributed transaction.  
            connection2.Open()  
  
            ' Do work in the second connection.  
  
        End Using  
    End Using  
  
    ' Commit the transaction.  
    transScope.Complete()  
End Using  

C#

using (TransactionScope transScope = new TransactionScope())  
{  
    using (SqlConnection connection1 = new   
       SqlConnection(connectString1))  
    {  
        // Opening connection1 automatically enlists it in the   
        // TransactionScope as a lightweight transaction.  
        connection1.Open();  
  
        // Do work in the first connection.  
  
        // Assumes conditional logic in place where the second  
        // connection will only be opened as needed.  
        using (SqlConnection connection2 = new   
            SqlConnection(connectString2))  
        {  
            // Open the second connection, which enlists the   
            // second connection and promotes the transaction to  
            // a full distributed transaction.   
            connection2.Open();  
  
            // Do work in the second connection.  
        }  
    }  
    //  The Complete method commits the transaction.  
    transScope.Complete();  
}  

Weitere Informationen

CLR-Integration und -Transaktionen