Compartir a través de


Participar en transacciones de servicios Web XML creados mediante ASP.NET

La compatibilidad de los servicios Web XML con las transacciones aprovecha la que se proporciona en Common Language Runtime, que está basada en el mismo modelo de transacciones distribuidas de Microsoft Transaction Server (MTS) y Servicios COM+. El modelo se basa en decidir de forma declarativa si un objeto participa en una transacción, en lugar de escribir código específico para controlar si una transacción se confirma o se deshace. Para un servicio Web XML creado mediante ASP.NET, puede declarar su comportamiento con respecto a las transacciones si establece la propiedad TransactionOption del atributo WebMethod aplicado a un método de servicio Web XML. Si se inicia una excepción durante la ejecución del método de servicio Web XML, la transacción se cancela automáticamente; por el contrario, si no se produce ninguna excepción, la transacción se confirma automáticamente.

La propiedad TransactionOption del atributo WebMethod especifica cómo participa un método de servicio Web XML en una transacción. Aunque este nivel declarativo representa la lógica de una transacción, se trata de un paso previo a la transacción real. Una transacción real tiene lugar cuando se produce el acceso de un objeto transaccional a un recurso de datos, como una base de datos o una cola de mensajes. La transacción asociada al objeto fluye automáticamente hasta el administrador de recursos apropiado. Un proveedor de datos de .NET Framework, como .NET Framework Data Provider para SQL Server o .NET Framework Data Provider para OLE DB, busca la transacción en el contexto del objeto y se inscribe en ella a través del DTC (Distributed Transaction Coordinator, Coordinador de transacciones distribuidas). La transacción completa se produce automáticamente.

Los métodos de servicio Web XML sólo pueden participar en una transacción como raíz de una nueva transacción. En este sentido, todas las interacciones con administradores de recursos, como los servidores Microsoft SQL Server, Microsoft Message Queuing (conocido también como MSMQ) y Microsoft Host Integration Server, conservan las propiedades ACID requeridas para ejecutar aplicaciones distribuidas sólidas. Los métodos de servicio Web XML que llaman a otros métodos de servicio Web XML participan en transacciones diferentes, ya que las transacciones no fluyen a través de los métodos de servicio Web XML.

Para participar en una transacción desde un método de servicio Web XML

  1. Declare un servicio Web XML.

    <%@ WebService Language="C#" Class="Orders" %>
    [Visual Basic]
    <%@ WebService Language="VB" Class="Orders" %>
    
  2. Agregue una directiva Assembly a System.EnterpriseServices.

    <%@ Assembly name="System.EnterpriseServices,Version=1.0.3300.0,Culture=neutral,PublicKeyToken=b03f5f7f11d50a3a" %>
    
  3. Agregue referencias a los espacios de nombres System.Web.Services y System.EnterpriseServices.

    using System.Web.Services;
    using System.EnterpriseServices;
    [Visual Basic]
    Imports System.Web.Services
    Imports System.EnterpriseServices
    
  4. Declare un método de servicio Web XML estableciendo en TransactionOption.RequiresNew el valor de la propiedad TransactionOption del atributo WebMethod.

    [ WebMethod(TransactionOption=TransactionOption.RequiresNew)]
    public int DeleteAuthor(string lastName)  
    [Visual Basic]
    < WebMethod(TransactionOption:=TransactionOption.RequiresNew)> _
    Public Function DeleteAuthor(lastName As String) As Integer
    

En el ejemplo de código siguiente se muestra un servicio Web XML que expone un único método de servicio Web XML denominado DeleteDatabase. Este método realiza una operación de base de datos dentro del ámbito de una transacción. Si la operación inicia una excepción, la transacción se detiene automáticamente; en caso contrario, se confirma automáticamente.

<%@ WebService Language="C#" Class="Orders" %>
<%@ Assembly name="System.EnterpriseServices,Version=1.0.3300.0,Culture=neutral,PublicKeyToken=b03f5f7f11d50a3a" %>

using System;
using System.Data;
using System.Data.SqlClient;
using System.Web.Services;
using System.EnterpriseServices;

public class Orders : WebService
{
   [ WebMethod(TransactionOption=TransactionOption.RequiresNew)]
   public int DeleteAuthor(string lastName)  
   {
      String deleteCmd = "DELETE FROM authors WHERE au_lname='" + 
                          lastName + "'" ;
      String exceptionCausingCmdSQL = "DELETE FROM NonExistingTable WHERE
                                       au_lname='" + lastName + "'" ;

      SqlConnection sqlConn = new SqlConnection(
        "Persist Security Info=False;Integrated Security=SSPI;database=pubs;server=myserver");

      SqlCommand deleteCmd = new SqlCommand(deleteCmdSQL,sqlConn);
      SqlCommand exceptionCausingCmd = new
                 SqlCommand(exceptionCausingCmdSQL,sqlConn);
   
      // This command should execute properly.
      deleteCmd.Connection.Open();
      deleteCmd.ExecuteNonQuery();

      // This command results in an exception, so the first command is
      // automatically rolled back.  Since the XML Web service method is
      // participating in a transaction, and an exception occurs, ASP.NET
      // automatically aborts the transaction.  The deleteCmd that
      // executed properly is rolled back.

      int cmdResult = exceptionCausingCmd.ExecuteNonQuery();

      sqlConn.Close();
       
      return cmdResult;
   }
}
[Visual Basic]
<%@ WebService Language="VB" Class="Orders" %>
<%@ assembly name="System.EnterpriseServices" %>

Imports System
Imports System.Data
Imports System.Data.SqlClient
Imports System.Web.Services
Imports System.Web.Util
Imports System.EnterpriseServices

Public Class  Orders

 <WebMethod(TransactionOption:=TransactionOption.RequiresNew)> _
 Public Function DeleteAuthor (lastName as String) as Integer   
     
   Dim deleteCmdSQL As String = "DELETE FROM authors WHERE au_lname='" + _ 
                          lastName + "'" 
   Dim exceptionCausingCmdSQL As String = "DELETE FROM " + _
      "NonExistingTable WHERE au_lname='" + lastName + "'" 

   Dim sqlConn As SqlConnection = New SqlConnection( _
        "Persist Security Info=False;Integrated Security=SSPI;database=pubs;server=myserver")

   Dim deleteCmd As SqlCommand  = New SqlCommand(deleteCmdSQL,sqlConn)
   Dim exceptionCausingCmd As SqlCommand  = New _
                 SqlCommand(exceptionCausingCmdSQL,sqlConn)
   
   ' This command should execute properly.
   deleteCmd.Connection.Open()
   deleteCmd.ExecuteNonQuery()

   ' This command results in an exception, so the first command is
   ' automatically rolled back. Since the XML Web service method is
   ' participating in a transaction, and an exception occurs, ASP.NET
   ' automatically aborts the transaction. The deleteCmd that
   ' executed properly is rolled back.

   Dim cmdResult As Integer = exceptionCausingCmd.ExecuteNonQuery()
   sqlConn.Close()
   
   Return cmdResult
  End Function
End Class

Nota Cuando no se llama al método que implementa el servicio Web XML debido a que se realiza una solicitud en Internet para el archivo con la extensión .asmx en el que reside o con el que está asociado, el valor de la propiedad TransactionOption no tiene ningún efecto. Esto puede ocurrir cuando la clase en la que reside el método es un miembro de un proyecto de Visual Studio .NET y no se llama al servicio Web XML mediante una clase de proxy. En Visual Studio .NET, las clases de proxy se generan al agregar una referencia Web.

Vea también

Procesar transacciones | TransactionOption (Enumeración) | WebMethodAttribute.TransactionOption (Propiedad) | Generar servicios Web XML mediante ASP.NET