Procedura: Scrivere uno unit test di SQL Server in esecuzione nell'ambito di una singola transazione
È possibile modificare unit test in modo che vengano eseguiti nell'ambito di una singola transazione.Se si adotta questo approccio, al termine del test è possibile eseguire il rollback di tutte le modifiche apportate dal test.Nelle procedure seguenti viene descritto come procedere:
Creare una transazione nello script di test Transact-SQL che utilizza BEGIN TRANSACTION e ROLLBACK TRANSACTION.
Creare una transazione per un singolo metodo di test in una classe di test.
Creare una transazione per tutti i metodi di test in una determinata classe di test.
Prerequisiti
Per alcune procedure di questo argomento è necessario che il servizio Distributed Transaction Coordinator sia in esecuzione nel computer in cui vengono eseguiti gli unit test.Per ulteriori informazioni, vedere la procedura alla fine di questo argomento.
Per creare una transazione tramite Transact-SQL
Per creare una transazione tramite Transact-SQL
Aprire uno unit test nella finestra di progettazione unit test di SQL Server.Per visualizzare la finestra di progettazione, fare doppio clic sul file del codice sorgente dello unit test.
Specificare il tipo di script per il quale si desidera creare la transazione.È ad esempio possibile specificare pre-test, test o post-test.
Immettere uno script di test nell'editor Transact-SQL.
Inserire le istruzioni BEGIN TRANSACTION e ROLLBACK TRANSACTION, come illustrato in questo semplice esempio.Nell'esempio viene utilizzata una tabella di database denominata OrderDetails che contiene 50 righe di dati:
BEGIN TRANSACTION TestTransaction UPDATE "OrderDetails" set Quantity = Quantity + 10 IF @@ROWCOUNT!=50 RAISERROR('Row count does not equal 50',16,1) ROLLBACK TRANSACTION TestTransaction
Nota
Non è possibile eseguire il rollback di una transazione dopo l'esecuzione dell'istruzione COMMIT TRANSACTION.
Per ulteriori informazioni sul funzionamento di ROLLBACK TRANSACTION con stored procedure e trigger, vedere la pagina nel sito Web Microsoft: ROLLBACK TRANSACTION (Transact-SQL).
Per creare una transazione per un singolo metodo di test
In questo esempio viene utilizzata una transazione di ambiente quando si utilizza il tipo TransactionScope.Per impostazione predefinita, nelle connessioni di esecuzione e con privilegi non verrà utilizzata la transazione di ambiente, poiché le connessioni sono state create prima dell'esecuzione del metodo.In SqlConnection è incluso un metodo EnlistTransaction che associa una connessione attiva a una transazione.Quando si creata una transazione di ambiente, questa viene registrata automaticamente come la transazione corrente ed è possibile accedervi tramite la proprietà Current.In questo esempio viene eseguito il rollback della transazione quando la transazione di ambiente viene eliminata.Se si desidera eseguire il commit delle modifiche apportate dopo l'esecuzione dello unit test, è necessario chiamare il metodo Complete.
Per creare una transazione per un singolo metodo di test
In Esplora soluzioni fare clic con il pulsante destro del mouse sul nodo Riferimenti nel progetto di test e scegliere Aggiungi riferimento.
Verrà visualizzata la finestra di dialogo Aggiungi riferimento.
Fare clic sulla scheda .NET.
Nell'elenco degli assembly fare clic su System.Transactions, quindi scegliere OK.
Aprire Visual Basic o il file C# per lo unit test.
Eseguire il wrapping delle azioni pre-test, test e post-test come illustrato nell'esempio di codice Visual Basic seguente:
<TestMethod()> _ Public Sub dbo_InsertTable1Test() Using ts as New System.Transactions.TransactionScope( System.Transactions.TransactionScopeOption.Required) ExecutionContext.Connection.EnlistTransaction(Transaction.Current) PrivilegedContext.Connection.EnlistTransaction(Transaction.Current) Dim testActions As DatabaseTestActions = Me.dbo_InsertTable1TestData 'Execute the pre-test script ' System.Diagnostics.Trace.WriteLineIf((Not (testActions.PretestAction) Is Nothing), "Executing pre-test script...") Dim pretestResults() As ExecutionResult = TestService.Execute(Me.PrivilegedContext, Me.PrivilegedContext, testActions.PretestAction) 'Execute the test script System.Diagnostics.Trace.WriteLineIf((Not (testActions.TestAction) Is Nothing), "Executing test script...") Dim testResults() As ExecutionResult = TestService.Execute(ExecutionContext, Me.PrivilegedContext, testActions.TestAction) 'Execute the post-test script ' System.Diagnostics.Trace.WriteLineIf((Not (testActions.PosttestAction) Is Nothing), "Executing post-test script...") Dim posttestResults() As ExecutionResult = TestService.Execute(Me.PrivilegedContext, Me.PrivilegedContext, testActions.PosttestAction) 'Because the transaction is not explicitly committed, it 'is rolled back when the ambient transaction is 'disposed. 'To commit the transaction, remove the comment delimiter 'from the following statement: 'ts.Complete() End Sub Private dbo_InsertTable1TestData As DatabaseTestActions
Nota
Se si utilizza Visual Basic, è necessario aggiungere Imports System.Transactions (oltre a Imports Microsoft.VisualStudio.TestTools.UnitTesting, Imports Microsoft.VisualStudio.TeamSystem.Data.UnitTesting e Imports Microsoft.VisualStudio.TeamSystem.Data.UnitTest.Conditions). Se si utilizza Visual C#, è necessario aggiungere using System.Transactions (oltre alle istruzioni using per Microsoft.VisualStudio.TestTools, Microsoft.VisualStudio.TeamSystem.Data.UnitTesting e Microsoft.VisualStudio.TeamSystem.Data.UnitTesting.Conditions).È inoltre necessario aggiungere un riferimento al progetto a tali assembly.
Per creare una transazione per tutti i metodi di test in una classe di test
Per creare una transazione per tutti i metodi di test in una classe di test
Aprire Visual Basic o il file C# per lo unit test.
Creare la transazione in TestInitialize ed eliminarla in TestCleanup, come illustrato nell'esempio di codice Visual C# seguente:
TransactionScope _trans; [TestInitialize()] public void Init() { _trans = new TransactionScope(); base.InitializeTest(); } [TestCleanup()] public void Cleanup() { base.CleanupTest(); _trans.Dispose(); } [TestMethod()] public void TransactedTest() { DatabaseTestActions testActions = this.DatabaseTestMethod1Data; // Execute the pre-test script // System.Diagnostics.Trace.WriteLineIf((testActions.PretestAction != null), "Executing pre-test script..."); ExecutionResult[] pretestResults = TestService.Execute(this.PrivilegedContext, this.PrivilegedContext, testActions.PretestAction); // Execute the test script // System.Diagnostics.Trace.WriteLineIf((testActions.TestAction != null), "Executing test script..."); ExecutionResult[] testResults = TestService.Execute(this.ExecutionContext, this.PrivilegedContext, testActions.TestAction); // Execute the post-test script // System.Diagnostics.Trace.WriteLineIf((testActions.PosttestAction != null), "Executing post-test script..."); ExecutionResult[] posttestResults = TestService.Execute(this.PrivilegedContext, this.PrivilegedContext, testActions.PosttestAction); }
Per avviare il servizio Distributed Transaction Coordinator
Per alcune procedure di questo argomento vengono utilizzati tipi dell'assembly System.Transactions.Prima di utilizzare queste procedure, è necessario assicurarsi che il servizio Distributed Transaction Coordinator sia in esecuzione nel computer in cui si eseguono gli unit test.In caso contrario, i test avranno esito negativo e verrà visualizzato il seguente messaggio di errore: "Il metodo di test NomeProgetto.NomeTest.NomeMetodo ha generato un'eccezione: System.Data.SqlClient.SqlException. MSDTC sul server 'NomeComputer' non è disponibile".
Per avviare il servizio Distributed Transaction Coordinator
Aprire il Pannello di controllo.
Nel Pannello di controllo aprire Strumenti di amministrazione.
In Strumenti di amministrazione aprire Servizi.
Nel riquadro Servizi fare clic con il pulsante destro del mouse sul servizio Distributed Transaction Controller e scegliere Avvia.
Lo stato del servizio verrà aggiornato in Avviato.A questo punto dovrebbe essere possibile eseguire unit test che utilizzano System.Transactions.
Importante |
---|
È possibile che il messaggio di errore seguente venga visualizzato anche se è stato avviato il servizio Distributed Transaction Controller: System.Transactions.TransactionManagerCommunicationException: Network access for Distributed Transaction Manager (MSDTC) has been disabled. Please enable DTC for network access in the security configuration for MSDTC using the Component Services Administrative tool. ---> System.Runtime.InteropServices.COMException: The transaction manager has disabled its support for remote/network transactions. (Exception from HRESULT: 0x8004D024). Se viene visualizzato questo errore, è necessario configurare il servizio Distributed Transaction Controller per l'accesso alla rete. Per ulteriori informazioni, vedere Abilitare l'accesso di rete DTC. |