Recientemente he leído muchos argumentos en contra del uso del patrón de repositorio con poderosos ORM como Entity Framework, ya que incorpora una funcionalidad de repositorio, junto con la funcionalidad de la Unidad de Trabajo también.
Otro argumento en contra del uso del patrón para una situación como las pruebas unitarias es que el patrón del repositorio es una abstracción permeable ya que las implementaciones más genéricas aprovechan IQueryable.
Los argumentos en contra del uso del patrón de repositorio tienen sentido para mí, pero los métodos alternativos de abstracción sugeridos son a menudo más confusos y parecen tan exagerados como el problema.
La solución de Jimmy Bogards parece ser una mezcla de volar las abstracciones, pero también presentar su propia arquitectura. https://lostechies.com/jimmybogard/2012/10/08/favor-query-objects-over-repositories/
Otro ejemplo de repositorios innecesariamente ... ¡pero use mi arquitectura! http://blog.gauffin.org/2012/10/22/griffin-decoupled-the-queries/
Otro ... http://www.thereformedprogrammer.net/is-the-repository-pattern-useful-with-entity-framework
No he encontrado un reemplazo claro o una alternativa al enfoque de patrón de repositorio "demasiado complejo" que no sea más arquitectónico en sí mismo.
fuente
Respuestas:
Creo que está combinando repositorios y repositorios genéricos.
Un repositorio básico solo interconecta su almacén de datos y proporciona métodos para devolver los datos
No filtra la capa de datos en su código a través de IQueryable u otras formas de pasar consultas aleatorias y proporciona una superficie de métodos inyectable y comprobable bien definida.
Un repositorio genérico le permite pasar su consulta como un ORM
Estoy de acuerdo en que no tiene mucho sentido usar un repositorio genérico encima de un ORM, que es básicamente otro repositorio genérico.
La respuesta es usar el patrón de repositorio básico para ocultar su ORM
fuente
La mayoría de los argumentos que menciona erróneamente se atribuyen a las características del patrón de Repositorio que no tiene.
Conceptualmente, un Repositorio como se definió originalmente en DDD es solo una colección de objetos en los que puede buscar o agregar. El mecanismo de persistencia detrás de esto se abstrae, por lo que como consumidor tienes la ilusión de que es una colección en memoria.
Una implementación de repositorio que tiene abstracciones con fugas (exponer,
IQueryables
por ejemplo) es una implementación de repositorio deficiente.Una implementación de repositorio que expone más que solo operaciones de recolección (por ejemplo, características de la Unidad de trabajo) es una implementación de repositorio deficiente.
¿Existen alternativas al repositorio para el acceso a datos? Sí, pero no están relacionados con los problemas que plantea en su pregunta.
fuente
Para mí, los repositorios, combinados con ORM u otras capas de persistencia DB, tienen estas desventajas:
Como:
4. Objeto Peligro de Dios: es posible que tengas la tentación de crear una clase de dios que cubra todo tu modelo o capa de acceso a datos. La clase de repositorio no solo contendría métodos Car, sino también métodos para todas las entidades.
En mi opinión, es mejor ofrecer al menos algunas oportunidades de consulta, para evitar el gran lío de muchos métodos de propósito único. No importa si es LINQ, un lenguaje de consulta propio o incluso algo tomado directamente del ORM (OK, tipo de problema de acoplamiento ...).
fuente
Si el propósito de la interfaz del repositorio es simular la base de datos para una prueba unitaria (= prueba aislada), la mejor abstracción es algo que es fácil de burlar.
Es difícil simular una interfaz de repositorio basada en un resultado IQueryable.
Desde el punto de vista de las pruebas unitarias
se puede burlar fácilmente
se puede burlar fácilmente solo si el simulacro ignora el contenido del parámetro de consulta.
no puede ser burlado fácilmente
fuente
No creo que el patrón de repositorio sea excesivo, si usa funciones lambda para realizar consultas. Especialmente cuando tiene que abstraer el ORM (en mi opinión, siempre debería hacerlo), entonces no me importarán los detalles de implementación del repositorio en sí.
Por ejemplo:
fuente