Compartir a través de


Consumo de un conjunto de datos desde un servicio web XML

La arquitectura del DataSet tiene un diseño desconectado, en parte para facilitar el transporte de datos a través de Internet. DataSet es "serializable" en que se puede especificar como entrada o salida desde servicios web XML sin necesidad de codificación adicional para transmitir el contenido del Conjunto de datos desde un servicio web XML a un cliente y de vuelta. DataSet se convierte implícitamente en una secuencia XML con el formato DiffGram, se envía a través de la red y, a continuación, se reconstruye a partir de la secuencia XML como dataSet en el extremo receptor. Esto proporciona un método sencillo y flexible para transmitir y devolver datos relacionales mediante servicios web XML. Para obtener más información sobre el formato DiffGram, vea DiffGrams.

En el ejemplo siguiente se muestra cómo crear un servicio web XML y un cliente que usan DataSet para transportar datos relacionales (incluidos los datos modificados) y resolver las actualizaciones de nuevo en el origen de datos original.

Nota:

La transmisión de instancias DataSet o DataTable como parte de las llamadas de servicio web XML no es segura si la entrada no es de confianza. Para obtener más información, vea Guía de seguridad de DataSet y DataTable. También se recomienda tener en cuenta siempre las implicaciones de seguridad al crear un servicio web XML. Para obtener información sobre cómo proteger un servicio web XML, vea Protección de servicios web XML creados mediante ASP.NET.

Creación de un servicio web XML

  1. Cree el servicio web XML.

    En el ejemplo, se crea un servicio web XML que devuelve datos, en este caso una lista de clientes de la base de datos Northwind y recibe un DataSet con actualizaciones de los datos, que el servicio web XML resuelve de nuevo en el origen de datos original.

    El servicio web XML expone dos métodos: GetCustomers, para devolver la lista de clientes y UpdateCustomers, para resolver las actualizaciones en el origen de datos. El servicio web XML se almacena en un archivo del servidor web denominado DataSetSample.asmx. En el código siguiente se describe el contenido de DataSetSample.asmx.

    <% @ WebService Language = "vb" Class = "Sample" %>  
    Imports System  
    Imports System.Data  
    Imports System.Data.SqlClient  
    Imports System.Web.Services  
    
    <WebService(Namespace:="http://microsoft.com/webservices/")> _  
    Public Class Sample  
    
    Public connection As SqlConnection = New SqlConnection("Data Source=(local);Integrated Security=SSPI;Initial Catalog=Northwind")  
    
      <WebMethod( Description := "Returns Northwind Customers", EnableSession := False )> _  
      Public Function GetCustomers() As DataSet  
        Dim adapter As SqlDataAdapter = New SqlDataAdapter( _  
          "SELECT CustomerID, CompanyName FROM Customers", connection)  
    
        Dim custDS As DataSet = New DataSet()  
        adapter.MissingSchemaAction = MissingSchemaAction.AddWithKey  
        adapter.Fill(custDS, "Customers")  
    
        Return custDS  
      End Function  
    
      <WebMethod( Description := "Updates Northwind Customers", EnableSession := False )> _  
      Public Function UpdateCustomers(custDS As DataSet) As DataSet  
        Dim adapter As SqlDataAdapter = New SqlDataAdapter()  
    
        adapter.InsertCommand = New SqlCommand( _  
          "INSERT INTO Customers (CustomerID, CompanyName) " & _  
          "Values(@CustomerID, @CompanyName)", connection)  
        adapter.InsertCommand.Parameters.Add( _  
          "@CustomerID", SqlDbType.NChar, 5, "CustomerID")  
        adapter.InsertCommand.Parameters.Add( _  
          "@CompanyName", SqlDbType.NChar, 15, "CompanyName")  
    
        adapter.UpdateCommand = New SqlCommand( _  
          "UPDATE Customers Set CustomerID = @CustomerID, " & _  
          "CompanyName = @CompanyName WHERE CustomerID = " & _  
          @OldCustomerID", connection)  
        adapter.UpdateCommand.Parameters.Add( _  
          "@CustomerID", SqlDbType.NChar, 5, "CustomerID")  
        adapter.UpdateCommand.Parameters.Add( _  
          "@CompanyName", SqlDbType.NChar, 15, "CompanyName")  
    
        Dim parameter As SqlParameter = _  
          adapter.UpdateCommand.Parameters.Add( _  
          "@OldCustomerID", SqlDbType.NChar, 5, "CustomerID")  
        parameter.SourceVersion = DataRowVersion.Original  
    
        adapter.DeleteCommand = New SqlCommand( _  
          "DELETE FROM Customers WHERE CustomerID = @CustomerID", _  
          connection)  
        parameter = adapter.DeleteCommand.Parameters.Add( _  
          "@CustomerID", SqlDbType.NChar, 5, "CustomerID")  
        parameter.SourceVersion = DataRowVersion.Original  
    
        adapter.Update(custDS, "Customers")  
    
        Return custDS  
      End Function  
    End Class  
    
    <% @ WebService Language = "C#" Class = "Sample" %>  
    using System;  
    using System.Data;  
    using System.Data.SqlClient;  
    using System.Web.Services;  
    
    [WebService(Namespace="http://microsoft.com/webservices/")]  
    public class Sample  
    {  
      public SqlConnection connection = new SqlConnection("Data Source=(local);Integrated Security=SSPI;Initial Catalog=Northwind");  
    
      [WebMethod( Description = "Returns Northwind Customers", EnableSession = false )]  
      public DataSet GetCustomers()  
      {  
        SqlDataAdapter adapter = new SqlDataAdapter(  
          "SELECT CustomerID, CompanyName FROM Customers", connection);  
    
        DataSet custDS = new DataSet();  
        adapter.MissingSchemaAction = MissingSchemaAction.AddWithKey;  
        adapter.Fill(custDS, "Customers");  
    
        return custDS;  
      }  
    
      [WebMethod( Description = "Updates Northwind Customers",  
        EnableSession = false )]  
      public DataSet UpdateCustomers(DataSet custDS)  
      {  
        SqlDataAdapter adapter = new SqlDataAdapter();  
    
        adapter.InsertCommand = new SqlCommand(  
          "INSERT INTO Customers (CustomerID, CompanyName) " +  
          "Values(@CustomerID, @CompanyName)", connection);  
        adapter.InsertCommand.Parameters.Add(  
          "@CustomerID", SqlDbType.NChar, 5, "CustomerID");  
        adapter.InsertCommand.Parameters.Add(  
          "@CompanyName", SqlDbType.NChar, 15, "CompanyName");  
    
        adapter.UpdateCommand = new SqlCommand(  
          "UPDATE Customers Set CustomerID = @CustomerID, " +  
          "CompanyName = @CompanyName WHERE CustomerID = " +  
          "@OldCustomerID", connection);  
        adapter.UpdateCommand.Parameters.Add(  
          "@CustomerID", SqlDbType.NChar, 5, "CustomerID");  
        adapter.UpdateCommand.Parameters.Add(  
          "@CompanyName", SqlDbType.NChar, 15, "CompanyName");  
        SqlParameter parameter = adapter.UpdateCommand.Parameters.Add(  
          "@OldCustomerID", SqlDbType.NChar, 5, "CustomerID");  
        parameter.SourceVersion = DataRowVersion.Original;  
    
        adapter.DeleteCommand = new SqlCommand(  
        "DELETE FROM Customers WHERE CustomerID = @CustomerID",  
         connection);  
        parameter = adapter.DeleteCommand.Parameters.Add(  
          "@CustomerID", SqlDbType.NChar, 5, "CustomerID");  
        parameter.SourceVersion = DataRowVersion.Original;  
    
        adapter.Update(custDS, "Customers");  
    
        return custDS;  
      }  
    }  
    

    En un escenario típico, el método UpdateCustomers estaría diseñado para detectar infracciones de simultaneidad optimista. Por motivos de simplicidad, el ejemplo no incluye esto. Para obtener más información sobre la simultaneidad optimista, consulte Simultaneidad optimista.

  2. Cree un proxy de servicio web XML.

    Los clientes del servicio web XML requieren un proxy SOAP para consumir los métodos expuestos. Puede hacer que Visual Studio genere este proxy automáticamente. Al establecer una referencia web a un servicio web existente desde Visual Studio, todo el comportamiento descrito en este paso se produce de forma transparente. Si desea crear la clase de proxy usted mismo, continúe con esta explicación. Sin embargo, en la mayoría de las circunstancias, el uso de Visual Studio para crear la clase de proxy para la aplicación cliente es suficiente.

    Se puede crear un proxy mediante la Herramienta de lenguaje de descripción de servicios web. Por ejemplo, si el servicio web XML se expone en la dirección URL http://myserver/data/DataSetSample.asmx, emita un comando como el siguiente para crear un proxy .NET de Visual Basic con un espacio de nombres de WebData.DSSample y almacenarlo en el archivo sample.vb.

    wsdl /l:VB -out:sample.vb http://myserver/data/DataSetSample.asmx /n:WebData.DSSample  
    

    Para crear un proxy de C# en el archivo sample.cs, emita el siguiente comando.

    wsdl -l:CS -out:sample.cs http://myserver/data/DataSetSample.asmx -n:WebData.DSSample  
    

    A continuación, el proxy se puede compilar como una biblioteca e importarse en el cliente del servicio web XML. Para compilar el código de proxy de .NET de Visual Basic almacenado en sample.vb como sample.dll, emita el comando siguiente.

    vbc -t:library -out:sample.dll sample.vb -r:System.dll -r:System.Web.Services.dll -r:System.Data.dll -r:System.Xml.dll  
    

    Para compilar el código de proxy de C# almacenado en sample.cs como sample.dll, emita el comando siguiente.

    csc -t:library -out:sample.dll sample.cs -r:System.dll -r:System.Web.Services.dll -r:System.Data.dll -r:System.Xml.dll  
    
  3. Cree un cliente de servicio web XML.

    Si desea que Visual Studio genere la clase de proxy de servicio web automáticamente, simplemente cree el proyecto de cliente y, en la ventana Explorador de soluciones, haga clic con el botón derecho en el proyecto y, a continuación, seleccione Agregar>referencia de servicio. En el cuadro de diálogo Agregar referencia de servicio , seleccione Avanzadas y, a continuación, seleccione Agregar referencia web. Seleccione el servicio web en la lista de servicios web disponibles (esto puede requerir proporcionar la dirección del punto de conexión de servicio web si el servicio web no está disponible en la solución actual o en el equipo actual). Si crea el proxy del servicio web XML usted mismo (como se describe en el paso anterior), puede importarlo en el código de cliente y consumir los métodos de servicio web XML.

    El código de ejemplo siguiente importa la biblioteca de proxy, llama a GetCustomers para obtener una lista de clientes, agrega un nuevo cliente y, a continuación, devuelve un conjunto de datos con las actualizaciones de UpdateCustomers.

    En el ejemplo se pasa el conjunto de datos devuelto por DataSet.GetChanges a UpdateCustomers porque solo es necesario pasar filas modificadas a UpdateCustomers. UpdateCustomers devuelve el DataSet resuelto, que puede fusionar en el DataSet existente para incorporar los cambios resueltos y cualquier información sobre errores de fila de la actualización. En el código siguiente se supone que ha usado Visual Studio para crear la referencia web y que ha cambiado el nombre de la referencia web a DsSample en el cuadro de diálogo Agregar referencia web .

    Imports System  
    Imports System.Data  
    
    Public Class Client  
    
      Public Shared Sub Main()  
        Dim proxySample As New DsSample.Sample ()  ' Proxy object.  
        Dim customersDataSet As DataSet = proxySample.GetCustomers()  
        Dim customersTable As DataTable = _  
          customersDataSet.Tables("Customers")  
    
        Dim rowAs DataRow = customersTable.NewRow()  
        row("CustomerID") = "ABCDE"  
        row("CompanyName") = "New Company Name"  
        customersTable.Rows.Add(row)  
    
        Dim updateDataSet As DataSet = _  
          proxySample.UpdateCustomers(customersDataSet.GetChanges())  
    
        customersDataSet.Merge(updateDataSet)  
        customersDataSet.AcceptChanges()  
      End Sub  
    End Class  
    
    using System;  
    using System.Data;  
    
    public class Client  
    {  
      public static void Main()  
      {  
        Sample proxySample = new DsSample.Sample();  // Proxy object.  
        DataSet customersDataSet = proxySample.GetCustomers();  
        DataTable customersTable = customersDataSet.Tables["Customers"];  
    
        DataRow row = customersTable.NewRow();  
        row["CustomerID"] = "ABCDE";  
        row["CompanyName"] = "New Company Name";  
        customersTable.Rows.Add(row);  
    
        DataSet updateDataSet = new DataSet();  
    
        updateDataSet =
          proxySample.UpdateCustomers(customersDataSet.GetChanges());  
    
        customersDataSet.Merge(updateDataSet);  
        customersDataSet.AcceptChanges();  
      }  
    }  
    

    Si decide crear la clase de proxy usted mismo, debe realizar los siguientes pasos adicionales. Para compilar el ejemplo, proporcione la biblioteca de proxy que se creó (sample.dll) y las bibliotecas de .NET relacionadas. Para compilar la versión de .NET de Visual Basic del ejemplo, almacenada en el archivo client.vb, emita el comando siguiente.

    vbc client.vb -r:sample.dll -r:System.dll -r:System.Data.dll -r:System.Xml.dll -r:System.Web.Services.dll  
    

    Para compilar la versión de C# del ejemplo, almacenada en el archivo client.cs, emita el comando siguiente.

    csc client.cs -r:sample.dll -r:System.dll -r:System.Data.dll -r:System.Xml.dll -r:System.Web.Services.dll  
    

Consulte también