repository-pattern - repositorio - patron unit of work
Repositorio genérico con EF 4.1 ¿cuál es el punto (3)
A medida que profundizo en el DbContext, DbSet y las interfaces asociadas, me pregunto por qué tendrías que implementar un repositorio "genérico" por separado en torno a estas implementaciones.
Parece que DbContext e IDbSet hacen todo lo que necesitas e incluyen la "Unidad de trabajo" dentro de DbContext.
Me estoy perdiendo algo aquí o parece que a la gente le gusta agregar otra capa de dependencia sin ningún motivo.
Estoy luchando con los mismos problemas, y la mockability para la prueba unitaria de las capas EF es importante. Pero me encontré con este excelente artículo que explica cómo configurar el EF 4.1 DbContext para que se pueda burlar, asegurándose de que su DbContext derivado implemente una interfaz genérica y exponga IDbSet en lugar de DbSet. Dado que estoy utilizando un enfoque de Base de datos, porque nuestra base de datos ya existe, simplemente modifiqué las plantillas T4 utilizadas para generar mi DbContext derivado para generarlo y devolver las interfaces IDbSet, así como derivar de mi interfaz genérica. De esta forma, todo el asunto se puede burlar fácilmente, y no es necesario implementar su propia unidad de trabajo o patrón de repositorio. Simplemente escriba su código de servicio para consumir su interfaz genérica, y cuando vaya a la prueba de la unidad, simplemente haga una prueba falsa de la interfaz genérica con datos de prueba específicos y listo.
Una razón para crear el repositorio es para que pueda ocultar la implementación de DBSet y DbContext si decide pasar de EntityFramework a otra cosa o viceversa.
Por ejemplo, estaba usando NHibernate y envolví todas las llamadas a ese marco dentro de mis clases de repositorio. Devuelven IEnumerable porque llega a ser "genérico" y mis repositorios tienen las operaciones CRUD estándar (actualización, eliminación, etc.). Hace tiempo que me mudé a Entity Framework. Al hacerlo, no necesité cambiar nada en mis clases de ViewModel o más allá porque apuntaban a mi repositorio, solo necesitaba cambiar el interior de mi repositorio. Esto hizo la vida mucho más fácil al migrar.
(Utilicé NHibernate porque nos estamos conectando a las ISeries, y en ese momento, no había implementaciones afectivas de costo que usaban EF con ISeries. El único disponible era pagar $ 12,000 a IBM por su DB2Connect)
En verdad tienes razón. DbContext
es una implementación del patrón de unidad de trabajo e IDbSet
es una implementación del patrón de repositorio.
Los repositorios son actualmente muy populares y se usan en exceso. Todos los usan simplemente porque hay docenas de artículos sobre la creación de repositorios para el marco de la entidad, pero nadie realmente describe los desafíos relacionados con esta decisión.
Las principales razones para usar el repositorio generalmente son:
- Ocultar EF de la capa superior
- Hacer código mejor comprobable
La primera razón es algún tipo de pureza arquitectónica y una gran idea de que si haces que tus capas superiores sean independientes de EF, más adelante podrás cambiar a otro marco de persistencia. ¿Cuántas veces viste tal cosa en el mundo real? Esta razón hace que trabajar con EF sea mucho más difícil porque su repositorio debe exponer muchas características adicionales que envuelven lo que EF permite de manera predeterminada.
Al mismo tiempo, envolver el código EF puede mantener su código mejor organizado y siguiendo la regla de Separación de preocupación. Para mí, esta puede ser la única ventaja real del repositorio y unidad de trabajo, pero debes comprender que seguir esta regla con EF hará que tu código sea más fácil de mantener y leer, pero en el esfuerzo inicial para crear tu aplicación será mucho más alto y para aplicaciones más pequeñas, esto puede ser una complejidad innecesaria.
La segunda razón es parcialmente correcta. La gran desventaja de EF es una arquitectura rígida que no se puede burlar, así que si quieres probar la capa superior de la unidad, debes envolver EF de alguna manera para permitir burlar su implementación. Pero esto tiene muchas otras consecuencias que describí here .
Sigo el blog de Ayende . Si alguna vez usaste NHibernate, probablemente conozcas sus artículos. Este tipo recientemente escribió varios artículos en contra del uso de repositorios con NHibernate, pero NHibernate es mucho mejor burlable.