No MVC, um modelo deve conter modelos de subvisão?

8

Alguns antecedentes:

Um colega e eu temos interpretações diferentes do MVC, o que significa que, dado o mesmo problema, estamos apresentando soluções radicalmente diferentes. Ele vem de um plano de fundo Java, onde todos os componentes do MVC podem modelar um objeto tradicionalmente, e eu sou de um plano de fundo Haskell e tenho pouca ou nenhuma experiência com OOP.

O espaço do problema:

O problema que estamos tentando modelar funciona um pouco como um ambiente de desktop. Temos uma noção da sessão do usuário (talvez o login, o plano de fundo da área de trabalho) e os processos na área de trabalho (por exemplo, iTunes, Finder, etc.), cada um com suas próprias propriedades de modelo (minimizadas, etc.).

Concordamos com o seguinte ponto: achamos que a HMVC é a melhor representação. Concordamos que temos dois objetos MVC Session((área de trabalho) e Process(aplicativo) e que não queremos Processque você tenha uma noção Sessionou um backlink.

Uma vez que discordamos, no entanto, é o significado principal do MVC e como isso afeta o local em que mantemos a lista de processos na área de trabalho dos usuários .

Sua interpretação:

Ele argumenta um ponto muito válido que tradicionalmente é fácil de modelar em código e em nosso sistema de renderização. Ele diz que a lista de processos deve ser uma lista de ProcessControllerobjetos dentro dos SessionControllerquais, por sua vez, têm seus modelos como objetos separados dentro deles. Isso significa que há uma quantidade significativa de estado dentro de ambos SessionControllere SessionModelque é relevante para o que SessionViewprecisa renderizar.

Isso parece estar muito em harmonia com o que conseguimos ler na internet em uma breve pesquisa.

Minha interpretação:

Minha interpretação requer a maior mudança de arquitetura e parece mais difícil de implementar no código, mas acredito que seja mais conceitualmente correto. Gostaria que alguém explicasse por que não é esse o caso, ou apresente um modelo diferente (se não o MVC) que se alinha com essa interpretação e destaque algumas forças e fraquezas dos dois padrões para que possamos tomar a decisão mais informada (nenhum de nós forte experiência em arquitetura de software).

Eu vejo o MVC como uma tríade com três componentes intercambiáveis: o Model, o Controllere o View. Isso concorda com o que eu posso ler na internet, e algumas fontes dirão coisas como 'visões, controladores e modelos com a mesma interface devem ser intercambiáveis ​​para efeitos diferentes'. A maneira como imagino que isso funcione é a seguinte:

  • Ao trocar o modelo, você está alterando a maneira como os dados são validados ou armazenados
  • Ao trocar o controlador, você está alterando o comportamento da página , mas nada que possa alterar o conteúdo de dados conceituais da página.
  • Quando você troca a visualização, está alterando a maneira como a página é exibida

A partir disso, raciocinei que, dado algum Modele View, a troca apenas do controlador não deve alterar os dados que a página renderiza inicialmente, porque o controlador deve alterar apenas o comportamento e não o 'conteúdo' da página. Eu acho que isso está alinhado com a visualização conceitual do controlador como um 'controlador de estação' em um sistema ferroviário, um plano da via férrea como modelo e a manifestação física real e a aparência / aparência dos trilhos (em diferentes sabores, digamos ' Real 'ou' Virtual 3D ') como a exibição.

Aqui é onde discordamos:

Argumento que, como os dados que serão exibidos para o usuário no SessionViewsão alterados pelos diferentes processos na área de trabalho (eu modelo os processos como dados relevantes ), eles SessionModeldevem conter a lista de instâncias de ProcessModel. Isso significa que o uso de qualquer aleatório SessionControllercom o mesmo SessionViewdeve mostrar conceitualmente os mesmos dados (processos na área de trabalho).

Ele argumenta que faz mais sentido Modelnunca se conhecer outro modelo. Isso significa que SessionControllerele teria uma lista de ProcessControllers e cada Controllerobjeto tem um link para seu modelo. Dado a SessionViewe o mesmo, SessionModelmas diferente, SessionControlleros dados exibidos para o usuário devem ser radicalmente diferentes.

Por favor, discuta a favor / contra cada interpretação e ajude-nos a alcançar o resultado mais informado.

Obrigado pelo seu tempo!

kvanberendonck
fonte
1
Trocar o controlador pode fazer com que o método do controlador renderize uma visão diferente ou retorne um objeto diferente. Portanto, seu argumento provavelmente só faz sentido se o controlador que você está trocando estiver em conformidade com uma interface / contrato específico. Portanto, não há garantia de que o novo controlador renderize os mesmos dados para a visualização; o controlador é obrigado apenas a renderizar ou devolver o que está programado para renderizar ou devolver.
9788 Robert
Portanto, o ponto de entrada para a renderização deve ser o controlador e não a visualização (com o controlador como argumento)?
kvanberendonck
1
Você, vindo de Haskell, deve se relacionar com o seguinte: Eu acho que o MVC é apenas um modelo abstrato de relacionamento entre partes de um programa, mas quais partes devem desempenhar a visão de função, modelo ou controlador depende do problema com o qual você se depara . Da mesma forma, a Teoria das categorias é apenas um conjunto de regras para ajudar a formalizar os relacionamentos entre objetos, mas não há uma definição rígida de quais objetos reais podem ser usados ​​com essas regras. A própria TC pode ser formalizada com a TC. O HMVC é um bom exemplo dessa ideia, pois você pode usar o MVC no MVC (embora não seja o mesmo tipo de recursão).
didierc
1
Existem também outras regras que determinam como as coisas devem ser escritas: SECO, SÓLIDO, BEIJO. Eles não estão em conflito com o MVC e certamente devem ser aplicados tanto (se não mais).
Didierc 6/12/14

Respostas:

6

A chave para entender o MVC está na separação das responsabilidades, pois o MVC é simplesmente SRP aplicado ao código da interface do usuário. Ele separa quais dados devem ser exibidos, de como exibi-los e de como manipular eventos de tela. Mas um detalhe importante (e muitas vezes esquecido) da definição original do MVC é que ele foi projetado para um nível muito mais granular. Por exemplo, você teria os objetos ButtonModel, ButtonView e ButtonController, "apenas" para apresentar um único botão em uma tela. A falta desse detalhe é o que causa tantas opiniões diferentes sobre o assunto. Você pode verificar a arquitetura Java Swing para ver o que quero dizer.

O objetivo do MVC é permitir que o código que serve a cada responsabilidade seja alterado sem afetar o código para os outros. Por exemplo, você seria capaz de ativar a renderização de (um componente) na tela sem precisar tocar na representação dos dados nem na lógica de manipulação de eventos. Então, até certo ponto, isso acompanha o que você diz aqui:

A partir disso, concluí que, dado qualquer modelo e exibição, trocar apenas o controlador não deve alterar os dados que a página renderiza inicialmente, porque o controlador deve alterar apenas o comportamento e não o 'conteúdo' da página. Eu acho que isso está alinhado com a visualização conceitual do controlador como um 'controlador de estação' em um sistema ferroviário, um plano da via férrea como modelo e a manifestação física real e a aparência / aparência dos trilhos (em diferentes sabores, digamos ' Real 'ou' Virtual 3D ') como a exibição.

No entanto, no seu contexto, o nível de granularidade está desativado; você tem um SessionView que parece ser responsável por uma tela inteira. Nesse nível, as responsabilidades são acopladas demais para separar completamente conforme pretendido pelo MVC, portanto, pode não fornecer todos os benefícios.

Seu problema é separar as três responsabilidades da interface do usuário (renderização, dados e manipulação de eventos) para sessões e processos, um total de seis. Devido ao nível de granularidade dos componentes (tela inteira), isso se torna impossível e causa a dissonância em que você se encontra.

Você deseja separar as responsabilidades de renderização e manipulação de eventos para Sessões e Processos, mas agrupará os dados deles. Seu colega deseja dissociar os dados, mas junte a manipulação de eventos.

Portanto, no final, esse é um problema do SRP. Minha saída seria diminuir o nível de granularidade até um ponto em que você possa separar claramente as sessões dos processos. Se você não pode fazer isso devido à economia, basta pesar os dois lados do acordo, escolher o pior e assinar como dívida técnica. Afinal, é disso que tratam as decisões de design. :)

MichelHenrich
fonte
Obrigado pelo seu tempo e comentários bem pensados. Temos muito o que pensar aqui! Espero que você não se importe se eu deixar isso em aberto por um tempo antes de escolher uma resposta para não desencorajar outras pessoas a compartilhar seu ponto de vista.
kvanberendonck
Eu estava pensando sobre isso hoje e me deparei com uma pergunta interessante: como será a renderização se os Processos estiverem no modelo Session? Como um SessionView obtém acesso aos ProcessControllers para entregar ao ProcessView?
precisa saber é o seguinte
1
Bem, com o MVC, você separa as Sessões dos Processos completamente (mais granular que o seu exemplo) ou cria um único Modelo, Visualização e Controlador para a tela inteira e trata as sessões e os processos como uma grande coisa (mais grosseira). Seu problema é a granularidade atual de seus objetos, onde você tenta separar as coisas, mas isso não permite uma separação limpa. Outros padrões, como MVP ou MVVM, funcionam melhor para "telas inteiras", em oposição ao MVC, que se destina aos pequenos elementos na tela.
precisa saber é o seguinte