tutorial patterns pattern mvc example delegate data model-view-controller design-patterns design architecture god-object

model view controller - patterns - Los modelos gordos y los controladores delgados suenan como crear modelos de Dios



mvc design pattern (3)

He estado leyendo muchos blogs que defienden los modelos gordos y el enfoque de los controladores delgados , especialmente. el campamento Rails. Como resultado, los enrutadores básicamente están averiguando qué método utilizar para llamar a qué controlador y todo lo que hace el controlador es llamar al método correspondiente en el modelo y luego mostrar la vista. Así que tengo dos preocupaciones aquí que no entiendo:

  1. El controlador y el enrutador realmente no están haciendo muchas tareas diferentes a solo llamar a un método en el modelo tipo Dios basado en la ruta.
  2. Los modelos están haciendo demasiado. Envío de correos electrónicos, creación de relaciones, eliminación y modificación de otros modelos, tareas de puesta en cola, etc. Básicamente ahora tiene objetos similares a los de Dios que se supone que deben hacer todo lo que pueda o no preocuparse con el modelado y el tratamiento de datos.

¿Dónde se traza la línea? ¿No es esto solo caer en el patrón de Dios?


Puede que no sea la mejor idea considerar Rails como un elemento básico del patrón de diseño de MVC. Dicho marco se creó con algunas deficiencias inherentes (lo elaboré un poco en una publicación diferente ) y la comunidad recién ahora comenzó a abordar las consecuencias. Puede ver el development DataMapper2 como el primer paso importante.

Alguna teoría

Las personas que dan ese consejo parecen estar afligidas por un concepto erróneo bastante común. Así que permítanme comenzar aclarando: Modelo, en el patrón de diseño MVC moderno, NO es una clase u objeto. El modelo es una capa.

La idea central detrás del patrón MVC es Separation of Concerns ( Separación de preocupaciones) y el primer paso es la división entre la capa de presentación y las capas del modelo. Al igual que la capa de presentación se descompone en controladores (instancias, responsables de tratar con la entrada del usuario), vistas (instancias, responsables de la lógica de la interfaz de usuario) y plantillas / diseños, también lo hace la capa del modelo.

Las principales partes en las que consiste la capa del modelo son:

  • Objetos de dominio

    También conocido como entidades de dominio, objetos comerciales u objetos modelo (no me gusta ese último nombre porque simplemente aumenta la confusión). Estas estructuras son lo que la gente suele llamar erróneamente "modelos". Son responsables de contener las reglas de negocio (todas las matemáticas y la validación para la unidad específica de lógica de dominio).

  • Abstracciones de almacenamiento:

    Por lo general, se implementa utilizando el patrón del mapeador de datos (no confunda con los ORMs , que han abusado de este nombre). Estas instancias generalmente tienen la tarea de almacenar y recuperar información en los objetos del dominio. Cada objeto de dominio puede tener varios mapeadores, al igual que hay varias formas de almacenamiento (DB, caché, sesión, cookies, / dev / null).

  • Servicios:

    Estructuras responsables de la lógica de la aplicación (es decir, interacción entre objetos de dominio e interacción entre objetos de dominio y abstracciones de almacenamiento). Deben actuar como la "interfaz" a través de la cual la capa de presentación interactúa con la capa del modelo. Esto es generalmente lo que en el código tipo Rails termina en los controladores.

También hay varias estructuras que pueden estar en los espacios entre estos grupos: DAOs , unidades de trabajo y repositories .

Ah ... y cuando hablamos (en el contexto de la web) sobre un usuario que interactúa con la aplicación MVC, no es un ser humano. El "usuario" es en realidad su navegador web.

Entonces, ¿qué hay de las deidades?

En lugar de tener un modelo aterrador y monolítico para trabajar, los controladores deben interactuar con los servicios. Pasa los datos de la entrada del usuario a un servicio específico (por ejemplo, MailService o RecognitionService ). De esta forma, el controlador cambia el estado de la capa del modelo, pero se hace utilizando una API clara y sin interferir con las estructuras internas (lo que causaría una abstracción con fugas).

Dichos cambios pueden provocar alguna reacción inmediata o solo afectan los datos que la instancia de vista solicita de la capa del modelo, o ambos.

Cada servicio puede interactuar con cualquier número (aunque, por lo general, solo un puñado) de objetos de dominio y abstracciones de almacenamiento. Por ejemplo, a RecogitionService no le importarían menos las abstracciones de almacenamiento para los artículos.

Notas de cierre

De esta forma se obtiene una aplicación que se puede probar en cualquier nivel, tiene bajo acoplamiento (si se implementa correctamente) y tiene una arquitectura claramente comprensible.

Sin embargo, tenga en cuenta: MVC no está diseñado para pequeñas aplicaciones. Si está escribiendo una página de libro de visitas usando el patrón MVC, lo está haciendo mal. Este patrón está destinado a hacer cumplir la ley y el orden en aplicaciones a gran escala.

Para las personas que usan PHP como idioma principal, esta publicación podría ser relevante. Es una descripción un poco más larga de la capa del modelo con algunos fragmentos de código.


Creo que se puede hacer una distinción entre un único modelo de grasa (posiblemente denominado Aplicación o Aplicación) y varios modelos de grasa divididos en grupos lógicos (Empresa, Cliente, Orden, Mensaje). El último es cómo estructurar mis aplicaciones, y cada modelo corresponde aproximadamente a una tabla de base de datos en una base de datos relacional o colección en una base de datos de documentos. Estos modelos manejan todos los aspectos de la creación, actualización y manipulación de los datos que conforman el modelo, ya sea que hablen a la base de datos o llamen a una API. El controlador es muy delgado y responsable por poco más que llamar al modelo apropiado y seleccionar una plantilla.


Si las clases "modelo" se implementan mal sí, su preocupación es relevante. Una clase modelo no debería estar haciendo Email (tareas de infraestructura).

La verdadera pregunta es qué implica el modelo en MVC. No está restringido a las clases de POCO con algunos métodos. Modelo en MVC significa lógica de datos y negocios. Trátelo como un superconjunto de los modelos POCO clásicos.

Ver ==== Controlador ==== Modelo ---> Capa de proceso empresarial -> Modelos principales

Agregue ensambles de infraestructura y capas de acceso a datos y use la inyección para entregarlo en el BPL, luego su proceso está usando el MVC como estaba previsto.

BPL puede invocar patrones UoW / Respository, y ejecutar reglas comerciales y llamar a las características de Infraestructura por medio de Objetos inyectados o patrones de interfaz.

Por lo tanto, la recomendación de mantener un controlador delgado no significa que la clase "persona" en un modelo Core clásico debe tener 50 métodos y llamar al correo electrónico directamente. Tienes razón al pensar que esto está mal.

El Controlador aún puede necesitar instanciar e inyectar clases de Infraestructura en el BPL o capa central si se llama directamente. Debe haber una capa empresarial o al menos clases que orquenen llamadas en las clases de modelo de Objeto clásico. Bueno, esa es mi "vista" de todos modos ;-)

Para una visión genérica de MVC, la descripción de la wiki http://en.wikipedia.org/wiki/Model%E2%80%93view%E2%80%93controller

Un pequeño blog que habla de la "M" en MVC. http://www.thedeveloperday.com/skinny-controllers/