Udostępnij za pośrednictwem


Transakcje lokalne

Transakcje w ADO.NET są używane, gdy chcesz powiązać wiele zadań razem, aby były wykonywane jako pojedyncza jednostka pracy. Załóżmy na przykład, że aplikacja wykonuje dwa zadania. Najpierw aktualizuje tabelę z informacjami o kolejności. Po drugie aktualizuje tabelę zawierającą informacje o spisie, debetowe uporządkowane elementy. Jeśli zadanie zakończy się niepowodzeniem, oba aktualizacje zostaną wycofane.

Określanie typu transakcji

Transakcja jest uważana za transakcję lokalną, gdy jest transakcją jednofazową i jest obsługiwana bezpośrednio przez bazę danych. Transakcja jest uważana za transakcję rozproszoną, gdy jest koordynowana przez monitor transakcji i używa mechanizmów bezpiecznych dla awarii (takich jak zatwierdzenie dwufazowe) na potrzeby rozpoznawania transakcji.

Każdy z dostawców danych programu .NET Framework ma własny Transaction obiekt do wykonywania transakcji lokalnych. Jeśli potrzebujesz transakcji do wykonania w bazie danych programu SQL Server, wybierz transakcję System.Data.SqlClient . W przypadku transakcji Oracle użyj dostawcy System.Data.OracleClient . Ponadto istnieje klasa, która jest dostępna do pisania kodu niezależnego DbTransaction od dostawcy, który wymaga transakcji.

Uwaga

Transakcje są najbardziej wydajne, gdy są wykonywane na serwerze. Jeśli pracujesz z bazą danych programu SQL Server, która intensywnie korzysta z jawnych transakcji, rozważ zapisanie ich jako procedur składowanych przy użyciu instrukcji Transact-SQL BEGIN TRANSACTION.

Wykonywanie transakcji przy użyciu pojedynczej Połączenie ion

W ADO.NET kontrolujesz transakcje za Connection pomocą obiektu . Możesz zainicjować transakcję lokalną za BeginTransaction pomocą metody . Po rozpoczęciu transakcji możesz zarejestrować polecenie w tej transakcji z Transaction właściwością Command obiektu. Następnie można zatwierdzić lub wycofać modyfikacje wprowadzone w źródle danych na podstawie powodzenia lub niepowodzenia składników transakcji.

Uwaga

Metoda EnlistDistributedTransaction nie powinna być używana dla transakcji lokalnej.

Zakres transakcji jest ograniczony do połączenia. Poniższy przykład wykonuje jawną transakcję składającą się z dwóch oddzielnych poleceń w try bloku. Polecenia wykonują instrukcje INSERT względem tabeli Production.ScrapReason w przykładowej bazie danych AdventureWorks SQL Server, które są zatwierdzane, jeśli nie są zgłaszane żadne wyjątki. Kod w catch bloku cofa transakcję, jeśli zostanie zgłoszony wyjątek. Jeśli transakcja zostanie przerwana lub połączenie zostanie zamknięte przed zakończeniem transakcji, zostanie ono automatycznie wycofane.

Przykład

Wykonaj następujące kroki, aby wykonać transakcję.

  1. Wywołaj metodę BeginTransactionSqlConnection obiektu, aby oznaczyć początek transakcji. Metoda BeginTransaction zwraca odwołanie do transakcji. To odwołanie jest przypisywane do SqlCommand obiektów wymienionych w transakcji.

  2. Transaction Przypisz obiekt do Transaction właściwości SqlCommand , która ma zostać wykonana. Jeśli polecenie jest wykonywane w połączeniu z aktywną transakcją, a Transaction obiekt nie został przypisany do Transaction właściwości Command obiektu, zgłaszany jest wyjątek.

  3. Wykonaj wymagane polecenia.

  4. Wywołaj metodę CommitSqlTransaction obiektu, aby zakończyć transakcję, lub wywołaj Rollback metodę , aby zakończyć transakcję. Jeśli połączenie zostanie zamknięte lub usunięte przed Commit wykonaniem metody lub Rollback , transakcja zostanie wycofana.

Poniższy przykład kodu przedstawia logikę transakcyjną przy użyciu ADO.NET z programem 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

Zobacz też