This Blog

Syndication

Search

Tags

Community

Email Notifications

Archives

Enlaces Recomendados

ADO.NET Entity Framework: LINQ To Entities, Entity SQL y Entity Services (II)

Hace un par de semanas escribía un primer post sobre ADO.NET Entity Framework complementario a la estupenda serie de posts que sobre esta temática ha venido realizando Jorge Serrano. En este post veíamos los fundamentos de ADO.NET Entity Framework, como construir un Entity Data Model (EDM) a partir de una cierta BD, y como realizar operaciones (de selección, inserción, actualización o borrado) mediante LINQ To Entities. La idea de este post es mostraros la flexibilidad de ADO.NET Entity Framework en cuanto a que para operar contra el EDM no sólo disponemos de LINQ To Entities, sino que tenemos otras dos opciones: Entity SQL (eSQL) y Entity Services. Empecemos.

Recordando los componentes de Entity Framework

Aunque Jorge Serrano ya nos explicó los componentes de un EDM, no está de más hacer un pequeño repaso de los mismos. Como ya comenté en el post anterior, una de las ideas claves de la nueva versión de ADO.NET es ahorrar tiempo a los desarrolladores a través de reducir la cantidad de código necesario para acceder a los datos, reducir el mantenimiento, facilitar la persistencia de los datos, etc. Todo ello es posible a través de la definición del correspondiente EDM, el cuál podemos consultar de las tres formas comentadas. Como siempre, una imagen vale más que 1000 palabras:

image Como veis, la clave de la realización de operaciones contra el EDM mediante cualquiera de los tres métodos está en un nuevo proveedor de datos: el Entity Client. Este proveedor permite interactuar contra el EDM mediante eSQL, que como veremos se trata de un nuevo lenguaje muy similar a T-SQL (sólo que las sentencias se ejecutan contra el EDM), Entity Services o LINQ To SQL que en este caso interactúan con el EDM a través de un objeto ObjectQuery (que representa una consulta que devuelve un cierto objeto con los datos).

Como nos comentaba Jorge Serrano, para entender como se realizan las operaciones contra el EDM es necesario conocer los componentes claves del mismo en la forma de tres capas:

  • Conceptual, definida mediante un archivo .CSDL (Conceptual Schema Definition Language, o en otras palabras un archivo XML con información relativa a las entidades del modelo), el cuál incluye las entidades y las relaciones tal y como la capa de negocio de la aplicación las conoce.
  • De asignación, definida con MSL (Mapping Schema Language, de nuevo otro XML con la información de mapeo entre la capa conceptual y la capa lógica), establece el mapeo entre las entidades del modelo conceptual y sus correspondencias con la BD.
  • Lógica, definida con SSDL (Store Schema Definition Language), y representa el esquema de la BD

image

Realizando consultas con eSQL

Como hemos comentado, este nuevo lenguaje similar a T-SQL nos permite interactuar con el EDM de manera similar a como estábamos acostumbrados a realizar operaciones contra una cierta BD en ADO.NET 2.0: define objetos específicos para la conexión al EDM, objeto EntityConnection, para devolver los datos en una consulta de selección, objeto DBDataReader, o ejecutar comandos eSQL contra el modelo...todas las clases que siguen estos objetos están definidas en el System.Data.EntityClient. Por lo tanto, el primer paso para realizar operaciones contra el EDM vía eSQL es instanciar la clase EntityConnection especificando la correspondiente cadena de conexión, que por cierto no es nada trivial:

EntityConnection ecConexion = new EntityConnection( @"metadata=.\CLIENTES_EDM.csdl|.\CLIENTES_EDM.ssdl|.\CLIENTES_EDM.msl;provider=System.Data.SqlClient;" + "provider connection string='Data Source=.\\SQLEXPRESS;" + "AttachDbFilename=\"C:\\Documents and Settings\\Administrator\\Desktop\\Labs LINQ\\Soluciones & Demos\\BD\\CLIENTES.mdf\";" + "Integrated Security=True;Connect Timeout=30;User Instance=True;MultipleActiveResultSets=True'" );

ecConexion.Open();

Como se observa, en la cadena de conexión es necesario especificar los distintos archivos de metadatos que configuran las distintas capas del EDM, así como la cadena de conexión para la BD. Una vez que hemos definido la cadena de conexión para el objeto EntityConnection, abrimos la conexión...esto se parece mucho al clásico ADO.NET...el siguiente paso es definir un comando eSQL mediante un objeto de tipo EntityCommand...dicho y hecho:

EntityCommand ecComando =
     new EntityCommand("SELECT  clientes.ID_Cliente,clientes.DireccionCliente," +
         "clientes.CiudadCliente FROM Entidades_BD_Clientes.Md_Clientes as clientes", ecConexion);

Lo que hemos hecho es definir una sentencia eSQL, que parece T-SQL, pero que no lo es porque estamos realizando las consultas contra una entidad del EDM (en este caso Md_Clientes que pertenece al EDM Entidades_BD_Clientes)...¿y cómo ejecutamos este comando? Pues a través del método ExecuteReader (para este caso en el que estamos realizando una Select) del objeto EntityCommand anterior. Lógicamente los resultados los recogeremos para su procesado en un objeto de tipo DbDataReader:

using (DbDataReader dbdrReader =
    ecComando.ExecuteReader(CommandBehavior.SequentialAccess))
{
    while (dbdrReader.Read())
    {
        Console.WriteLine(dbdrReader["ID_Cliente"] + ", " +
            dbdrReader["DireccionCliente"] + " " +
            dbdrReader["CiudadCliente"]);
    }
}

Sin duda espectacular...y la salida por pantalla correspondiente es la siguiente:

image

Realizando consultas con Entity Services (u Object Services)

Finalmente, y para concluir el post, vamos a ver la tercera opción para realizar operaciones contra un EDM: los Entity Services (u Object Services). Esta alternativa permite devolver estructuras de información del EDM a través del método CreateQuery asociado al objeto ObjectContext (y que implementa una interfaz de tipo ObjectQuery<T>), que acepta una instrucción eSQL o LINQ To Entities con parámetros que define una consulta que recuperará una cierta lista de entidades. Así, un ejemplo de ejecutar una sentencia eSQL con Entity Services sería:

Console.WriteLine("Entity Services");
string sCiudad = "Santander";
//ObjectQuery
ObjectQuery<ClientesModel.Md_Clientes> esQuery =
    ModeloClientes.CreateQuery<ClientesModel.Md_Clientes>
    ("SELECT VALUE c FROM Md_Clientes AS c WHERE c.CiudadCliente=@CiudadCliente",
    new ObjectParameter("CiudadCliente",sCiudad));

foreach (var c in esQuery)
{
    Console.WriteLine(c.ID_Cliente);
}

Y la correspondiente salida por pantalla sería la siguiente:

image

Y hasta aquí la segunda entrega de la serie de posts sobre ADO.NET Entity Framework. En el siguiente post os presentaré una utilidad muy interesante para realizar operaciones contra el modelo. Espero que el post os haya resultado interesante.

Published 8/2/2008 0:30 por Juan Carlos González Martín

Comparte este post:

Comentarios

# re: ADO.NET Entity Framework: LINQ To Entities, Entity SQL y Entity Services (II)@ Tuesday, August 19, 2008 12:42 PM

Buenos días. Estoy intentando seguir tus consejos y comentarios para crear una aplicación usando Entity framework. La aplicación está separada en capas y la duda es ¿cuántas instancias del modelo de entidades (el ObjectContext) debe haber en la aplicación?. Si cada vez que consulto los datos creo una nueva me da problemas porque no puedo asociar entidades de una instancia con entidades de otra, y sin embargo en varios ejemplos vistos en internet lo hacen así. ¿Alguna sugerencia?

Gracias y sigue así con tus posts que son muy buenos

Atag

# re: ADO.NET Entity Framework: LINQ To Entities, Entity SQL y Entity Services (II)@ Friday, September 26, 2008 9:09 AM

Buenas Atag,

Deberías tener una instancia de ObjectContext para esas operaciones en las que quiereas asociar entidades porque EF preserva la identidad de entidades, por lo que ante ObjectContext diferentes tiene sentido lo que te está pasando.

Un saludo

JC's

Juan Carlos González Martín