O suporte a transações para serviços Web XML aproveita o suporte no Common Language Runtime, que se baseia no mesmo modelo de transação distribuída encontrado no Microsoft Transaction Server (MTS) e nos Serviços COM+. Este modelo baseia-se na determinação explícita se um objeto participa de uma transação, em vez de escrever um código específico para lidar com a delegação e os retornos de chamada de uma transação. Para um serviço Web XML criado usando ASP.NET, você pode declarar o comportamento de transação de um serviço Web XML definindo o atributo TransactionOption do atributo WebMethod que se aplica a um método de serviço Web XML. Se uma exceção for lançada quando o método XML Web Service for executado, a transação termina automaticamente, caso contrário, se nenhuma exceção ocorrer, a transação será delegada automaticamente;
O atributo TransactionOption do atributo WebMethod especifica como um método de serviço Web XML participa de uma transação. Embora este nível de declaração represente uma lógica de transação, ele está a um passo da transação real. A transação real ocorre quando um objeto de transação acessa uma fonte de dados (como um banco de dados ou uma fila de mensagens). As transações associadas a esse objeto fluem automaticamente para o gerenciador de recursos apropriado. Um provedor de dados .NET Framework como o .NET Framework Data Provider (para SQL Server ou OLE DB) procura transações no contexto de um objeto e as cataloga por meio de um Coordenador de Transações Distribuídas (DTC, Distributed Transaction Coordinator). Todas as transações são geradas automaticamente.
Os métodos de serviço Web XML só podem participar de uma transação que seja a raiz de uma nova transação. Como raiz de uma nova transação, todas as interações com gerenciadores de recursos (como servidores que executam o Microsoft SQL Server, o Microsoft Message Queuing e o Microsoft Host Integration Server) mantêm as propriedades ACID necessárias para executar aplicativos distribuídos robustos. Os métodos de serviço Web XML que chamam outros métodos de serviço Web XML participam de transações diferentes porque as transações não fluem através de métodos de serviço Web XML.
Declare um serviço Web XMLusando transações de métodos de serviço Web XML
.
[C#]
<%@ WebService Language="C#" Class="Pedidos" %>
[Visual Básico]
<%@ WebService Language="VB" Class="Orders" %>
Adicione uma instrução assembly a System.EnterpriseServices.
<%@ Assembly name="System.EnterpriseServices,Version=1.0.3300.0,Culture=neutral,PublicKeyToken=b03f5f7f11d50a3a" %>
Adicione referências aos espaços de nome de domínio System.Web.Services e System.EnterpriseServices.
[C#]
usando System.Web.Services;
usando System.EnterpriseServices;
[Visual Básico]
Importa System.Web.Services
Imports System.EnterpriseServices
declara um método de serviço Web XML e define a propriedade TransactionOption do atributo WebMethod como TransactionOption.RequiresNew.
[C#]
[WebMethod(TransactionOption=TransactionOption.RequiresNew)]
public int DeleteAuthor(string sobrenome)
[Visual Básico]
<WebMethod(TransactionOption:=TransactionOption.RequiresNew)> _
Função pública DeleteAuthor(lastName As String) As Integer
O exemplo de código a seguir mostra um serviço Web XML usando um único método de serviço Web XML, chamando DeleteDatabase. Este método de serviço Web XML executa uma operação de banco de dados no escopo de uma transação. Se a operação do banco de dados lançar uma exceção, a transação será automaticamente interrompida; caso contrário, a transação será automaticamente confirmada;
[C#]
<%@ WebService Language="C#" Class="Pedidos" %>
<%@ Assembly name="System.EnterpriseServices,Version=1.0.3300.0,Culture=neutral,PublicKeyToken=b03f5f7f11d50a3a" %>
usando o sistema;
usando System.Data;
usando System.Data.SqlClient;
usando System.Web.Services;
usando System.EnterpriseServices
classe pública Orders: WebService;
{
[WebMethod(TransactionOption=TransactionOption.RequiresNew)]
public int DeleteAuthor(string sobrenome)
{
String deleteCmd = "DELETE FROM autores WHERE au_lname='" +
sobrenome + "'" ;
String exceçãoCausingCmdSQL = "DELETE FROM NonExistingTable WHERE
au_lname='" + sobrenome + "'" ;
SqlConnection sqlConn = new SqlConnection(
"Persistir informações de segurança = falso; segurança integrada = SSPI; banco de dados = pubs; servidor = myserver")
;
Exceção SqlCommandCausingCmd = novo
SqlCommand(exceptionCausingCmdSQL,sqlConn);
// Este comando deve ser executado corretamente.
deleteCmd.Connection.Open();
deleteCmd.ExecuteNonQuery();
// Este comando resulta em uma exceção, então o primeiro comando é
// revertido automaticamente, pois o método de serviço da Web XML é
// participando de uma transação e ocorre uma exceção, ASP.NET
// cancela automaticamente a transação. O deleteCmd que
// executado corretamente é revertido.
int cmdResult = exceçãoCausingCmd.ExecuteNonQuery(
)
;
}
}
[Visual Básico]
<%@ WebService Language="VB" Class="Pedidos" %>
<%@ assembly name="System.EnterpriseServices" %>
Importa Sistema
ImportaçõesSystem.Data
Importa System.Data.SqlClient
Importa System.Web.Services
Importa System.Web.Util
Importa
pedidos de classe pública
System.EnterpriseServices<WebMethod(TransactionOption:=TransactionOption.RequiresNew)> _
Função pública DeleteAuthor (sobrenome como String) como número inteiro
Dim deleteCmdSQL As String = "DELETE FROM autores WHERE au_lname='" + _
sobrenome + "'"
Dim exceçãoCausingCmdSQL As String = "DELETE FROM" + _
"NonExistingTable WHERE au_lname='" + lastName + "'"
Dim sqlConn As SqlConnection = New SqlConnection( _
"Persistir informações de segurança = falso; segurança integrada = SSPI; banco de dados = pubs; servidor = meu servidor")
Dim deleteCmd As SqlCommand = New SqlCommand (deleteCmdSQL, sqlConn)
Dim exceçãoCausingCmd As SqlCommand = Novo _
SqlCommand(exceptionCausingCmdSQL,sqlConn)
'Este comando deve ser executado corretamente.
excluirCmd.Connection.Open()
deleteCmd.ExecuteNonQuery()
'Este comando resulta em uma exceção, então o primeiro comando é
'revertido automaticamente, pois o método de serviço Web XML é revertido.
'participando de uma transação, e ocorre uma exceção, ASP.NET
' anula automaticamente a transação. O deleteCmd que
'executado corretamente é revertido
Dim cmdResult As Integer = exceçãoCausingCmd.ExecuteNonQuery().
sqlConn.Close()
Retorna cmdResult
Função final
Fim da aula