Generar clases POCO en diferentes proyectos al proyecto con el modelo Entity Framework


Estoy tratando de usar el Patrón de repositorio con EF4 usando VS2010.

Para este fin estoy usando la generación de código POCO haciendo clic derecho en el diseñador del modelo de entidad y haciendo clic en Agregar elemento de generación de código. Luego selecciono la plantilla POCO y obtengo mis clases.

Lo que me gustaría poder hacer es estructurar mi solución en proyectos separados para las clases Entity (POCO) y otro proyecto para el modelo entity y el código del repositorio.

Esto significa que mi proyecto MVC podría usar las clases POCO para vistas fuertemente tipeadas, etc. y no tener que saber sobre el repositorio o tener una referencia a él.

Para conectarlo todo junto tendré otro proyecto separado con interfaces y usaré IoC.

Suena bien en mi cabeza ¡simplemente no sé cómo generar las clases en su propio proyecto! Puedo copiarlos y luego cambiar los espacios de nombres en ellos, pero quería evitar el trabajo manual cada vez que cambio el esquema en la base de datos y quiero actualizar mi modelo.

Gracias

Author: Max, 2010-03-17

4 answers

En realidad, las plantillas de T4 en EF 4.0 se diseñaron teniendo en cuenta este escenario:)

Hay 2 plantillas:

  • Uno para las Entidades mismas (i. e. ModelName.tt)
  • Uno para el ObjectContext (i. e. ModelName.Context.tt)

Usted debe poner el ModelName.tt archivo en su proyecto POCO, y simplemente cambie la plantilla para que apunte al archivo EDMX en el proyecto consciente de persistencia.

Suena raro Lo sé: Ahora hay una dependencia, pero está en T4 tiempo de generación, no en tiempo de compilación! ¿Y eso debería estar bien? Debido a que la asamblea POCO resultante sigue siendo completamente ignorante persistencia.

Vea los pasos 5 y 6 de esto: http://blogs.msdn.com/adonet/pages/walkthrough-poco-template-for-the-entity-framework.aspx{[16] para más.

Espero que esto ayude

Alex

 38
Author: Alex James,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2010-03-18 05:46:59

@Nick,

  1. Para forzar la regeneración de las entidades POCO, solo tiene que hacer clic con el botón derecho en el archivo main .tt y seleccionar "Ejecutar herramienta personalizada". Esto lo obligará a regenerar sus clases POCO con sus cambios actualizados a la .modelo edmx.
  2. ¿Hay algún problema con que siga adelante y haga clic derecho en el modelo y seleccione "Generar base de datos desde el modelo..."a pesar de que usted no está generando necesariamente la base de datos? Que lo más probable es deshacerse de su " Error 11007...'.
  3. Creo que es equivalente a un "Código detrás". No sé más que eso.

Otra cosa a tener en cuenta sobre el enlace que Alex dio. Una vez que moví mi archivo main .tt a un proyecto diferente, el archivo que se generó a partir de la ".Context.tt " file no compilaba porque le faltaban referencias a los archivos POCO que estaban ubicados en un espacio de nombres diferente (porque quería que mi ObjectContext estuviera en un dominio diferente a mis archivos POCO). Tuve que modificar the". Context.tt " file to had a using Poco.Namespace (donde Poco.Namespace es el nombre del espacio de nombres donde se generaron los archivos POCO). Esto permitió a mi proyecto compilar.

Joel

 6
Author: hjoelr,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2010-05-24 03:03:49

Para EF5 + DbContext generator: Es fácil mover su Name.Context.tt a un proyecto diferente. Sin embargo, tendrá que hacer referencia a las clases modelo. Puede hacer esto manualmente, pero esto requerirá que lo cambie cada vez que se genere el código. También puede usar el mismo espacio de nombres para ambos proyectos. Esto es válido y funcionará, pero creo que es un mal diseño. Otra alternativa es cambiar la plantilla T4 (Name.Context.tt).

Cambie esto (línea 43):

using System;
using System.Data.Entity;
using System.Data.Entity.Infrastructure;
<#
if (container.FunctionImports.Any())
{
#>

A esto:

using System;
using System.Data.Entity;
using System.Data.Entity.Infrastructure;
<#
if (modelNamespace != codeNamespace)
#>
using <#=code.EscapeNamespace(modelNamespace)#>;
<#
if (container.FunctionImports.Any())
{
#>

Esto comprobará si el espacio de nombres del modelo difiere del espacio de nombres del código, si es así, insertará el uso requerido para hacer referencia a las clases del modelo.

 3
Author: J.G. Hek,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2013-10-10 14:12:36

Me he encontrado con un error grave al usar este enfoque combinado con proyectos de Datos Dinámicos y controles. Básicamente, obtendrá un error.

"No se pudo determinar una MetaTabla. No se pudo determinar una MetaTable para la fuente de datos 'EntityDataSource1' y no se pudo inferir una de la URL de la solicitud. Asegúrese de que la tabla está asignada a la fuente de datos, o que la fuente de datos está configurada con un tipo de contexto válido y un nombre de tabla, o que la solicitud es parte de un DynamicDataRoute."

 1
Author: Josh Simerman,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2010-06-18 15:16:34