Introducción a Web Services con .NET II

En la primera parte de nuestro tutorial vimos como podemos elaborar un Web Service con .NET que es capaz de devolver un mensaje y como generar la aplicación en FLEX para consumir el mismo y mostrarlo. En esta parte del tutorial veremos algo mucho mas interesante y de mucha utilidad para nuestras aplicaciones que consiste en enlazar datos de nuestro Web Service a una base de Datos SQL Server 2005 Express Edition, entender los conceptos básicos de ADO.NET y como desplegarlos de igual manera en FLEX.


Herramientas y conceptos básicos

SQL Server 2005 Express Edition es un manejador de bases de datos ideal para almacenar los datos de aplicaciones pequeñas y personales. Cuenta con el SQL Server Management Studio Express que es el IDE para elaborar nuestras consultas, procedimientos almacenados, seguridad, funciones etc. La base de datos con la que trabajaremos se encuentra en el QuickStart del SDK del .NET Framework 2.0 llamada Store.Te invitamos a descargar las herramientas necesarias para completar el tutorial.

Sql Management Studio Express
Sql Server Management Studio Express

Una vez que ya tenemos las herramientas necesarias para empezar a desarrollar debemos de entender lo esencial de ADO.NET . ADO.NET es una colección de clases y objetos del .NET Framework que nos proporciona acceso a fuentes de datos. Cuando estamos en un desarrollo y nos enfrentamos al acceso a datos existen varias maneras de hacerlo, una es mediante el DataSet o la otra posibilidad es el DataReader, que debemos de igual manera saber emplear dependiendo de nuestra situación, es decir si ocupamos una u otra o la combinación de las 2, ya que cada una de estas tienen sus ventajas y desventajas.

Si tu proyecto requiere de acceso rápido a datos es decir solo lectura y no vas a hacer ninguna operación de inserción (INSERT) o actualización (UPDATE) lo más recomendable es usar un DataReader ya que es mucho más rápido que un DataSet. Una de sus desventajas es que lo hace en modo conectado y como mencionamos anteriormente solo es de modo lectura.

Por el otro lado tenemos a el DataSet, este nos permite hacer operaciones tanto de lectura como de escritura es decir (SELECT, INSERT Y UPDATE).Normalmente trabaja en conjunto con un DataAdapter para efectuar estas operaciones y este se encarga de procesar la sentencia SQL, la conexión y el resultado pasarlo al DataSet. Además el Dataset trabaja en modo desconectado ya que guarda temporalmente todos los datos como un objeto en el servidor. Es importante mencionar que los Datasets los ocupamos para hacer operaciones complejas en la base de datos, incluso el Dataset puede tener múltiples DataTables o lo que es lo mismo tablas de la base de datos, lo que el DataReader es incapaz de hacer ya que solo soporta una tabla de la base de datos. Las desventajas del Dataset es que el acceso a los datos es más lento.

En resumen si quieren acceso rápido y de solo lectura les recomiendo el DataReader , si lo que quieren es efectuar operaciones de inserción o actualización o quieren combinar múltiples tablas de la base de datos lo que les recomiendo es el Dataset.

Conexión del Web Service a una base de datos

Ahora que contamos con la parte teórica necesaria empecemos a codificar nuestro Web Service para acceder a nuestros datos. Lo primero que haremos es un sencillo método para verificar si mi conexión con la base de datos es correcta. Aislaremos la cadena de conexión en el archivo Web.config, este archivo es para configurar parámetros de la aplicación y que es donde almacenaremos nuestra cádena de conexión y utilizaremos el Configuration Manager para acceder a este. Es importante mencionar que es buena práctica poner nuestras cadenas de conexión en el archivo Web.Config y no embeberla en nuestro código ,ya que de esta manera si cambia el motor de base de datos no será necesario volver a compilar nuestra aplicación.

En VWD dirijamonos a archivo abrir y abramos el proyecto del tutorial pasado, si no cuentas con el te recomendamos pegar el siguiente código en un nuevo proyecto de ASP.NET Web Service (para la creación de un nuevo proyecto ve la primera parte del tutorial aqui).

[FTF w="450" h="200"]using System;
using System.Web;
using System.Web.Services;
using System.Web.Services.Protocols;
using System.Data;
using System.Data.SqlClient;
using System.Configuration;

[WebService(Namespace = "http://localhost/webserviceclass/")]
[WebServiceBinding(ConformsTo = WsiProfiles.BasicProfile1_1)]
public class Service : System.Web.Services.WebService
{
public Service () {

//Eliminar la marca de comentario de la línea siguiente si utiliza los componentes diseñados
//InitializeComponent();
}

[WebMethod (Description="Método de prueba que me regresa una cadena")]
public string HelloWorld() {
return “Hola a todos”;
}

[WebMethod(Description = "Método para probar la conexión con la base de datos")]
public bool TestConnection()
{
//CADENA DE CONEXION
string strConn = ConfigurationManager.ConnectionStrings["StoreAccess"].ConnectionString;

//OBJETO DE CONEXION SQL, SI LA BASE DE DATOS ES ACCESS
//EL OBJETO SERIA OleDbConnection
SqlConnection sqlConn=new SqlConnection();

//ASIGNO LA CADENA DE CONEXIÓN
sqlConn.ConnectionString=strConn;

try{

//ABRO LA CONEXION

sqlConn.Open();

//SI TODO ES CORRECTO REGRESAME VERDADERO
return true;
}

//DE LO CONTRARIO REGRESAME FALSO
catch(Exception ex){
return false;
}

//FINALMENTE CIERRA LA CONEXION
finally{
sqlConn.Close();
}

}

}

[/FTF]

Primeramente en la línea 6 y 7 de nuestro código tenemos que importar dos librerias, una para mi acceso a datos (System.Data.SqlClient)y la última para poder acceder a la configuración de la aplicación (Web.Config) mediante el ConfigurationManager.

En la línea 25 generamos un método que me regresa solamente un valor booleano y me dira si mi conexión con el motor de base de datos es correcta. En la línea 28 declaro una variable de tipo cadena que es la que le pasare a mi objeto SQL de conexión posteriormente y que es igual a la cadena de conexión con el identificador “StoreSQL” que se encontrara en el archivo Web.Config. Antes de continuar asignemos en el archivo Web.config nuestra cadena de conexión. El archivo Web.config está en el explorador de soluciones, si no lo pueden ver y es nuevo su proyecto inicien la depuración (F5) y les aparecerá una pantalla diciendoles si lo quieren agregar. Existe otra manera de agregarlo y es dando clic derecho sobre nuestro URL den el explorador de soluciones>agregar nuevo elemento>Archivo de configuración web.

Explorador de soluciones
Explorador de soluciones

Una vez que estamos en el archivo Web.config en el nodo de connectionstrings asignaremos el siguiente código.

[FTF W="450" H="200"]














[/FTF]

Primero lo que hacemos es añadir una etiqueta add con un atributo name para asignar un identificador a nuestra conexión con datos y posteriormente el atributo connectionString para la cadena de conexión pertinente con el nombre de nuestra base de datos en este caso llamado Store. Existen varias cadenas de conexión dependiendo el contexto donde se encuentren , una buena fuente para consultar cadenas de conexión de distintos manejadores de bases de datos es www.connectionstrings.com

Una vez finalizado la configuración en Web.Config regresemos a nuestro archivo Service.cs y continuemos analizando el código. En la línea 31 declaro un objeto de conexión y posteriormente le paso la propiedad ConnectionString que sera igual a la variable strConn. Enseguida en la línea 36 abro un bloque try para ocupar el método open del objeto de conexion. Si todo marcha bien me regresara true el Web Service, de lo contrario saltara a la línea número 36 y cachara la excepción y me regresara false. En nuestro bloque finally pase lo que pase cerrara la conexión. Generalmente cuando abrimos conexiones con datos es casi obligado para desarrolladores meterlos en bloques try, catch, finally por si ocurre una excepción cacharla y manejala.

Probemos nuestro Web Service iniciando la depuración (F5) y nos debe aparecer en nuestro navegador predeterminado 2 métodos, nuestro famoso HelloWorld y ahora nuestro método TestConnection.

Navegador con métodos
Navegador mostrando métodos del Web Service

Demos clic en TestConnection y si todo está correcto deberá devolvernos nuestro método el valor de true. En caso contrario nos devolverá false. Los errores más comunes que podemos encontrar aquí son que la cadena de conexión este mal escrita en el archivo Web.Config, que el nombre al que nos referimos en el Configuration Manager no sea igual al nombre llave (“StoreSQL”) que asignamos en el archivo Web.Config.

Conexion exitosa
Conexión exitosa del Web Service

Ahora pasemos a la parte interesante que es acceder a los datos y desplegaros en nuestro WebService para posteriormente consumirlo en FLEX con un DataGrid. Para este ejemplo ocuparemos el DataSet en conjunto con un DataTable para devolver los datos a FLEX.

Lo interesante de ocupar y regresar un tipo de datos DataTable en un Web Service de .NET es que FLEX lo interpretara como un ArrayCollection, y obvio este atributo lo podemos hacer [Bindable] para posteriormente asignarlo a un componente que en este caso será un DataGrid.

Agregaremos un método llamado getDataTable que me regresará un DataTable apartir de un DataSet. Recordemos que los DataSets son capaces de guardar múltiples tablas.Nuestro Web Service se debe ver como el siguiente código con el nuevo método.

[FTF W="450" H="200"]using System;
using System.Web;
using System.Web.Services;
using System.Web.Services.Protocols;
using System.Data;
using System.Data.SqlClient;
using System.Configuration;

[WebService(Namespace = "http://localhost/webserviceclass/")]
[WebServiceBinding(ConformsTo = WsiProfiles.BasicProfile1_1)]
public class Service : System.Web.Services.WebService
{
public Service () {

//Eliminar la marca de comentario de la línea siguiente si utiliza los componentes diseñados
//InitializeComponent();
}

[WebMethod (Description="Método de prueba que me regresa una cadena")]
public string HelloWorld() {
return “Hola a todos”;
}

[WebMethod(Description = "Método para probar la conexión con la base de datos")]
public bool TestConnection()
{
//CADENA DE CONEXION
string strConn = ConfigurationManager.ConnectionStrings["StoreSQL"].ConnectionString;

//OBJETO DE CONEXION SQL, SI LA BASE DE DATOS ES ACCESS
//EL OBJETO SERIA OleDbConnection
SqlConnection sqlConn=new SqlConnection();

//ASIGNO LA CADENA DE CONEXIÓN
sqlConn.ConnectionString=strConn;

try{

//UTILIZO EL MÉTODO OPEN PARA
//
sqlConn.Open();

//SI TODO ES CORRECTO REGRESAME VERDADERO
return true;
}

//DE LO CONTRARIO REGRESAME FALSO
catch(Exception ex){
return false;
}

//FINALMENTE CIERRA LA CONEXION
finally{
sqlConn.Close();
}

}
//METODO QUE ME REGRESA UN DATATABLE
[WebMethod(Description = "Método que me devuelve un DataTable")]
public DataTable getDataTable()
{
//DECLARO MI CADENA DE CONEXION ALMACENADA
//EN EL ARCHIVO WEB.CONFIG
string strConn = ConfigurationManager.ConnectionStrings["StoreSQL"].ConnectionString;

//DECLARO MI OBJETO DE CONEXION
SqlConnection sqlConn = new SqlConnection();

//ASIGNO LA CADENA DE CONEXIÓN AL OBJETO DE CONEXION
sqlConn.ConnectionString = strConn;

//SQL A LA TABLA PRODUCTS
string strSQL = “SELECT * FROM PRODUCTS”;

//DECLARO EL ADAPTADOR DE DATOS
SqlDataAdapter da = new SqlDataAdapter(strSQL,sqlConn);

//DECLARO EL DATASET
DataSet dsProductos = new DataSet();

//LLENO EL DATASET
da.Fill(dsProductos);

//REGRESO
return dsProductos.Tables[0];

}

}

[/FTF]

Como pueden observar es muy sencillo el código, tengo entonces un método que me regresara un DataTable. Dentro del método primero declaro una variable que contendra la cadena de conexión (línea 65) almacenada en el archivo Web.config. Posteriormente declaro un objeto de conexión (línea 68) y con la propiedad ConnectionString del objeto de conexión lo asigno (línea 71) a mi variable que contiene la cadena. Una vez hecho esto declaro en una variable la consulta que deseo ejecutar (línea 74), en este caso a la tabla de PRODUCTS. Enseguida declaro un adaptador de datos (línea 77) y le paso como parametros la consulta y el objeto de conexión. Despues declaro un DataSet (línea 80) y con el método Fill del SqlDataAdapter lleno el DataSet (línea 83) con los registros. Finalmente regreso el DataTable (línea 86) haciendo referencia al método Tables con el índice en 0 ya que no tenemos más tablas en está consulta.

Me despliega un XML en un formato llamado DiffGram, este tipo de formato es para representar a un DataSet y además es capaz de identificar cambios en el DataSet. Además nos muestra ya los datos provenientes de la base en una mánera fácil de leer.

DiffGram
DiffGram

Una vez desplegando nuestra tabla de Datos en nuestro navegador pasemos a FLEX implementar lo último para desplegar los datos.

Consumir el Web Service en FLEX

Primeramente iniciaremos con agregar un botón y un DataGrid. Al botón le asignaremos una etiqueta llamada “Obtener DataSet”.Estos los ubicaremos en la parte inferior de nuestros primeros componentes que hicimos en la parte 1 del tutorial como se ve en la figura.

DataGrid y Boton en FLEX
Botón y Datagrid en FLEX

Pasaremos a la vista de código y veremos que tenemos el botón y el DataGrid. Lo que deseamos es que al dar click al botón mande llamar a mi Web Service y llene de registros el DataGrid. Empecemos por agregar un script justo debajo de la etiqueta de application y modificar algunas cosas en mi MXML. El código es el siguiente:

[FTF W="450" H="200"]


//IMPORTO LAS CLASEs NECESARIAS PARA MANEJAR EL DATASET Y EL EVENTO
import mx.collections.ArrayCollection;
import mx.rpc.events.ResultEvent;

[Bindable]
private var arrProductos:ArrayCollection

//FUNCION QUE ME LLENA UN DATAGRID
private function llenaDataGrid(event:ResultEvent):void{

arrProductos=event.result.diffgram.NewDataSet.Table;
}

]]>



width="201" click="mifWebService.HelloWorld()" />

click="mifWebService.getDataTable()"/>

[/FTF]

Después de agregar la etiqueta script importamos las clases necesarias, ArrayCollection y ResulEvent para manejar los resultados de mi llamado.Posteriormente declaro con el metadatag [Bindable] una variable arrProductos de tipo ArrayCollection y que será igual a los resultados obtenidos por el Web Service. Noten que despues de event.result tengo diffgram.NewDataSet.Table que es como me lo regresa el Web Service (ver figura de diffgram).Enseguida lo que hacemos es declarar una función llamada llenaDataGrid que le pasamos como parámetro una variable llamada event de tipo ResultEvent.

Nota importante
Para ver el comportamiento del tipo de datos que me esta interpretando event dentro de la función, comentemos la línea donde asignamos la variable arrProductos y asignemos un punto de interrupción en la fúncion llenaDataGrid. Iniciemos la depuración y encontraremos principalmente dos objetos this y event. Si hacemos una exploración el en objeto event vean como el DataTable de .NET es interpretado como un ArrayCollection

Sesión de depuración
Sesión de depuración

En lo que respecta al MXML tenemos la etiqueta WebService asignandole un id para referenciarlo y el WSDL donde reside nuestro Web Service. Dentro de la etiqueta Web Service abro una etiqueta llamada operation y con el atributo name hago referencia a la operación o al método en mi Web Service (getDataTable) si tuvieramos mas operaciones y las quiero convocar puedo abrir tantas etiquetas de tipo operation como yo desee para diferentes métodos , además tiene el atributo result que es igual a la funcion que ya declaramos dentro del bloque script y que maneja los resultados.

En líneas posteriores encontramos las etiquetas correspondientes a el botón y el DataGrid que agregamos. El botón tiene el atributo click que es igual al identificador del Web Service con el método que pretendemos llamar (getDataTable). Por último la etiqueta DataGrid tiene el atributo dataprovider que es igual a la variable arrProductos.

Si todo esta correcto corramos la aplicación , demos click en el boton obtenerDataSet y veamos los resultados como se ve en la figura

DataGrid con resultados
DataGrid con resultados

Conclusión:
Esta es una manera de trabajar con Web Services de .NET y FLEX accediendo a datos. No obstante existe una mejor manera que nos beneficia en desempeño tanto del lado del cliente como del lado del servidor si la cantidad de datos es mayor, aunque implica un poco de mayor código. En el siguiente tutorial veremos como podemos implementar esta manera para mejorar el rendimiento, además de manejar posibles fallas del lado del servidor dentro de FLEX.

Israel Gaytán es un Adobe Certified Professional y desarrollador enfocado en la creación de RIAs. Desarrolla bajo la plataforma.NET y ha trabajado con Flash, Flash remoting (AMFPHP, .NET) y Flash Media Server.

Sitio Web:http://riata.wordpress.com

66 Comentarios

  1. JORGE

    Hola Israel, me uno a los comentarios, la aplicacio me lanza un error 1010.
    busque y para los Runtime errors Adobe dice que es como si estubiera intentando llmar una propiedad que no existe.
    A ver si nos ayudas con esto para seguir avanzando.
    Te agradezco mucho
    bye

  2. Israel Gaytan

    Ok voy a ver que es lo que puede estar sucediendo. Todos estan trabajando con visual studio 2008? o 2005 en el error 1010?

    Voy a hacer el tutorial con 2008 a ver que me sucede pero no debiera tener ese error.

  3. JORGE

    Amigos encontre la respuesta al problema, usando el debugger.
    Si se fijan en la imagen del debugger que muestra israel se daran cuenta que las propiedades diffgram y tables esta definidas.
    Si ven su debugger pues no existen a esto se atribuye el error 1010.
    bueno el caso es que si reemplazan en la funcion “llenarDataGrid” el valor para arrProductos con el siguiente:
    arrProductos=event.result.Tables.Table.Rows;
    se poblara el datagrid

    la funcion completa seria
    private function llenaDataGrid(event:ResultEvent):void{
    arrProductos=event.result.Tables.Table.Rows;
    }

    espero les funcione y me hayan entendido
    Bye

  4. Jonathan Griguol

    Hola gente, tenia el mismo problema del error 1010, yo estoy trabajando con el Visual Studio 2005… probé con la solución que publicó JORGE y ahora funciona bien, de todos modos, no me queda claro cual era el problema, creo que saberlo aclararia muchas cosas a tener en cuenta para seguir consumiendo webServices de .NET
    Por cierto… como debería hacer para acceder a un solo registro? más alla del filtro en la consulta claro. Ej:

    SELECT * FROM PRODUCTOS WHERE prodId=1

    Y mostrar el resultado en un form, no en un DataGrid.

    Saludos
    Jonathan.

    @flaswolver: supongo que creando un nuevo metodo con el respectivo “insert”, “update” o lo que sea.

  5. oscar

    k tal amigos yo tengo un problema lo que pasa es que yo uso un web service y funciona al seguir los pasos del articulo de arriba pero yo uso una ventana como componente y pues cuando hago los mismos pasos del articulo pero en mi componente no lo hace me pasama la aplicacion el codigo que uso para mi componente es el siguiente:

    [Event("change", type="mx.events.Event")]

    y lo llamo de mi aplicacion:

    y al ejecutar no me muestra nada o en ocaciones si queda el componentes de load pasmado ojala y alguien pudiera ayudarme con esto

  6. Yiseth

    Israel imaginate que el codigo esta perfecto… pero sucede que no me sirve, digo esta perfecto porque me produce un error. que me aconsejas?

  7. Hernán Herrera

    Muy buen tutorial para comenzar con flex y . net :razz:

    lo hice y me salia un error al tomar los datos de event.result, lo correji de la siguiente manera:

    //arrProductos=event.result.diffgram.NewDataSet.Table;
    arrProductos=event.result.Tables.Table.Rows;

  8. Mario Rodriguez

    Hola, excelente tutorial nos salvas la vida bien seguido maestro Israel, estoy provando todo esto para desde el webservice generar graficos en flex!!, por si alguien le interesa

  9. Mario

    Necesito ayuda, necesito subir lo que hice en Flex llamando a un web service .NET, pero no se como hacer despues de hacer correr laaplicacion, ya que si lo cambio de posiciion no me carga los datos del web service

  10. willy

    Hola, me parece excelente el documento presentado. Ahora quiero hacerles una pregunta:
    Queiro consumir un web service con .net, pero el servidor donde esta ubicado el web service es un servidor apache. hay alguna forma de hacer el desarrollo desde .net con el wsdl que me estan proporcionando, sin importar el servidor o el lenguaje en el cual fue desarrollado el web service.
    muchas gracias por su colaboración y ayuda.
    si tienen algun ejemplo les agradezcao

  11. hugo4295

    Excelente tutorial, y con las correciones perfectas para poder consumir el WS de .net, estoy desarrollando una aplicacion sobre vs2008 y SQLServer 2008 de microsoft todo esta excelente :razz: , ya estan mas aplias mis ideas gracias a estos tutos, suerte…

Deja un comentario

Tu dirección de correo electrónico no será publicada. Los campos necesarios están marcados *

Puedes usar las siguientes etiquetas y atributos HTML: <a href="" title=""> <abbr title=""> <acronym title=""> <b> <blockquote cite=""> <cite> <code class="" title="" data-url=""> <del datetime=""> <em> <i> <q cite=""> <strike> <strong> <pre class="" title="" data-url=""> <span class="" title="" data-url="">

Acerca de Made In Flex

Made In Flex es una comunidad de desarrolladores de Apache Flex creada en 2006.

Apache Flex, anteriormente conocido como Adobe Flex, es un SDK (kit de desarrollo de software) para crear aplicaciones enriquecidas - multiplataforma basadas en Adobe Flash donado por Adobe a la fundación Apache in 2011 y promocionado a proyecto de primer nivel en Diciembre de 2012.

Actualmente estamos cambiando muchos aspectos del sitio web para ofrecer un sitio útil para toda la comunidad que tenga en cuenta las necesidades actuales.

Últimas Fotos

Instalador de Apache Flex

Entrar o Registrase