Tengo una pregunta sobre DDD y el patrón de repositorio.DDD - Cómo implementar repositorios de alto rendimiento para buscar
Supongamos que tengo un repositorio de clientes para la raíz del agregado del cliente. Los métodos Get & Find devuelven el agregado totalmente poblado, que incluye objetos como Address, etc. Todo bien. Pero cuando el usuario busca un cliente en la interfaz de usuario, solo necesito un 'resumen' del agregado, solo un objeto plano con información resumida.
Una forma de lidiar con esto es llamar al método find en el repositorio de forma normal, y luego en la capa de aplicación asignar cada agregado de cliente a un DTO ClientSearchResult/CustomerInfo y enviarlos de vuelta al cliente.
Pero mi problema con esto es el rendimiento; cada agregado de Cliente puede requerir múltiples consultas para completar todas las asociaciones. Entonces, si mis criterios de búsqueda coinciden con 50 clientes, es un gran golpe en la base de datos para recuperar datos que ni siquiera voy a necesitar.
El otro problema es que puedo desear incluir datos resumidos sobre el cliente que se encuentren fuera del límite raíz agregado del Cliente, como la fecha del último pedido hecho, por ejemplo. El pedido tiene su propio agregado y, por lo tanto, para obtener la información del pedido del cliente, tendría que llamar al OrderRepository, lo que también degrada el rendimiento.
Así que ahora creo que me quedo con dos opciones:
Añadir un método Find adicional a la CustomerRepository que devuelve una lista de estos objetos de resumen, realice una consulta eficiente.
Crear un propósito construido CustomerInfoRepository de sólo lectura, que acaba de encontrar el método descrito en 1.
Pero ambas cosas siento que estoy yendo en contra de los principios de la DDD. Mis repositorios heredan de una base genérica: Repositorio donde T: IAggregateRoot. Estos objetos de información resumida no son agregados, y son de un tipo diferente a T, por lo que realmente el # 1 va en contra del diseño.
Quizás para el n. ° 2 crearía un SearchRepository abstracto sin la restricción IAggregateRoot?
Hay muchos escenarios similares en mi dominio.
¿Cómo implementaría este escenario?
Gracias, de Dave
actualización
Después de leer la respuesta de Theo, creo que voy a ir con la opción # 2 y crear un SearchRepository especializada dentro de mi infraestructura orientada a estos escenarios. La capa de aplicación (servicios WCF) puede llamar a estos repositorios que completan los DTO de resumen directamente en lugar de asignar entidades de dominio a DTO.
**** **** Actualización 2
Aunque hice esta hace un año pensé que acababa de añadir que desde entonces he descubierto CQRS que está orientada a la solución de este problema exacto.Udi Dahan (http://www.udidahan.com/) y Greg Young (http://codebetter.com/gregyoung/) han escrito mucho al respecto. Si está creando una aplicación distribuida con DDD, ¡CQRS es para usted!
Tienes razón, no son ni entidades ni objetos de valor. Creo que realmente lo que estaba preguntando es, ¿dónde encajarían estos objetos de resumen en el dominio? Creo que la respuesta es: no lo hacen. Como usted dice, son solo para fines informativos, similar a mostrar información del informe; no encapsulan reglas comerciales. Eso fue un video interesante por cierto - sorprendido, ya lo he encontrado antes :) Gracias, Dave –
Great answer. Estoy enfrentando exactamente el mismo problema y tu respuesta fue muy esclarecedora. –
Aquí hay una pregunta relacionada. Algunos de los enlaces en la respuesta de Mohamed Abed fueron muy útiles. http://stackoverflow.com/questions/7365913/how-do-read-only-database-views-fit-into-the-repository-pattern?lq=1 –