È possibile avviare una transazione in una stored procedure e quindi eseguirne il rollback o eseguirne il commit in una procedura nidificata?Come utilizzare le transazioni su più stored procedure?
risposta
Commit e rollback hanno effetti diversi
- COMMIT decrementa @@ TRANCOUNT
- ROLLBACK lo spinge di nuovo a zero
Questo accade perché SQL Server in realtà non supporta le transazioni nidificate.
Se si impegnano o il rollback in una stored nidificato (non di transazione), allora verrà generato l'errore 266 a causa di una mancata corrispondenza @@ TRANCOUNT su start e l'ingresso
La questione rollback può essere risolto utilizzando SET XACT_ABORT ON che è "auto rollback" (semplicemente) e sopprime l'errore 266.
Il problema del commit ... non è possibile. Tuttavia, è possibile controllare dove si verifica notando @@ TRANCOUNT sulla voce di registro memorizzata e impegnando solo se zero.
Per la movimentazione delle transazioni corrette, vedere le mie risposte qui per favore: Nested stored procedures containing TRY CATCH ROLLBACK pattern? e Have I to count transactions before rollback one in catch block in T-SQL?
Non è possibile eseguire il commit in una procedura nidificata, ma l'avvio di una transazione racchiude tutte le procedure nidificate al suo interno. Quindi la transazione è buona per tutte le stored procedure nidificate all'interno della transazione. Nelle transazioni distribuite, l'integrità dei dati incrocia persino i confini della macchina.
http://msdn.microsoft.com/en-us/library/ms188929(v=SQL.90).aspx
è necessario abbinare il vostro BEGIN TRAN e si impegna nella stessa SPROC
Se poi si chiama un altro SPROC che ha anche una transazione, conseguente BEGIN TRAN/commit coppie TRAN di incremento e decremento @ @Trancount rispettivamente.
La transazione è impegnata sul 'ultima' COMMIT TRAN (@@ TRANCOUNT = 1)
Tuttavia, qualsiasi ROLLBACK sarà sempre il rollback della transazione.
MSDN ha una buona spiegazione.
Sì, è possibile. Con linguaggi di programmazione come C#, quando si passa la connessione e l'oggetto transazione con il comando. se qualcosa è preso come sbagliato rispetto al rollback della transazione:
string customerConnection = "Connection";
string query = "insert into temp values ('Data2','data1','data2','data3')";
string query2 = "update tempcst set data = 'Hello data'";
SqlConnection myConnection = new SqlConnection(customerConnection);
myConnection.Open();
SqlTransaction myTrans = myConnection.BeginTransaction();
Try{
int result = executeNonQuery(query, myConnection, myTrans, "");
i = executeNonQuery(query2, myConnection, myTrans, "");
myTrans.Commit();}
catch{
myTrans.Rollback();
myConnection.Close();
}