Quem está seguindo deve saber da conversa que estava acontecendo no post sobre MVC e Camadas onde se falava sobre a “localização” , ou melhor, se o Modelo pertence na camada de business ou não.
Em primeiro lugar vamos clarificar o que significa estar ou não na camada de business. Podemos entender “estar na camada de business” como estar no andar “business” ou dominio. Ora o andar de dominio vem a seguir ao de apresentação e antes da integração. É o andar central de uma arquitetura em 5 andares.
Ou podemos entender “camada business” como “o pacote das classes do andar de business” ou seja, em qual pacote ou sub-pacote estaria a classe.
A seguir mostro o esquema classico do MVC
Normalmente quando usamos o padrão MVC estamos interessados em dar alguma margem ao programador final de poder implementar variações do modelo ou da view de uma forma intercambiável, como menos ou mais facilidade tecnologica – isso não está em causa agora. Contudo o controller está sempre o dominio de quem implmentou o MVC. O propósito e objetivo final da estrutura está no Controller e normalmente ele é inalterável. Em alguns casos pode ser configurável ou extensivel mas nunca é possivel moficiá-lo por completo. O Controller é onde existe a razão de ser do MVC.
A View e o Model , são , portanto, normalmente não implementados, ou implementados em versões básicas. Por exemplo, a view é normalmente implementada numa versão simples já que sem ela não haveria funcionalidade nenhuma. Por exemplo, no swing a view é o look & feel e sempre existe um que funciona ( o look and feel padrão da JVM). Por exemplo, no Apache pivot é implementa uma view padrão, no JSF temos a implementação de referencia. Uma exceção a esta regra seria por exemplo o struts, onde a view serão as JSP criadas pelo programador.
Portanto um diagrama que leva em conta as implementações seria mais ou menos assim:
Estas implementações são classes java ou se traduzem em classes java e pertencem em algum pacote/ camada/ andar. Como disse no outro post o MVC é um padrão que se aplica em única camada, então por consequência das tudo está no mesmo andar que é o de apresentação ( supondo que estamos usando o MVC nesse andar, onde é mais comum).
Mas peguemos o exemplo do JSF em que o model é um managed bean. Em tese o managed bean pertence na camada de apresentação e ele contém regras relacionadas à apresentação. A chamada “lógica de tela”. Mas é possivel, por exemplo, usar um EJB Session Bean para fazer o papel do manged bean. E agora , em qual camada pertence ? Esta é a essência da conversa discutida no outro post.
Existe aqui uma pequena falacia de confundir tecnologias com camadas/andares e assumir que o EJB pertence na camada de negocio. O que não é verdade.Se usarmos EJB como porta de entrada e webservices ou message beans estamos usando na camada de integração, mas não vamos prender nisto que não interessa agora. Vamos assumir que o EJB é a nossa implementação do andar de business. Ora, ou usar também como managed bean não estamos misturandos as coisas ? Sim estamos. E o fazemos para facilidade prática.
Estamos fundindo duas partes , duas camadas e tornando-a “uma” sem costuras ( seamlessly – dai o JBoss Seam que faz exactamente isto).
Mas lá porque as estamos fundindo tecnicamente, não significa que não uma separação entre as duas. É como dizer que o ombro é o mesmo que a cabeça porque entre eles existe um pescoço que os une “sem costuras”. Mesmo sendo unidos podemos identificar as várias partes.
O MVC usado no JSF continua usando como managed bean um objeto java que é o que ele exige, o fato desse objeto java ser tambem um EJB é mera coincidência. Por outro lado o negocio está definido no EJB e o fato dele também um managed bean é mera coincidencia. O objeto pertence nas duas camadas simultaneamente. Isto é possivel ? sim, e está o seam ai para provar, mas isso não significa que seja algo desejável ou seja boa arquitetura. Mas funciona e é “simples”. Porque não é bom ? Ora, porque está acoplado. O principio de separação de repsonsabilida deixa claro que um objeto deve ter apenas uma responsabilidade. Ser de duas camadas obviamente é ter mais do que uma responsabilidade.
Bom, então o managed bean, não importa como é implementado pertence no andar/ camada de apresentação ,porque o MVC onde ele é usado pertence nessa camada/andar. Mas isto é válido para todos os modelos de MVC ?
Um outro ponto é discussão é a interface / contrato do modelo. Por exemplo, no JSF se exige um objeto com caracteristicas de bean. No swing se exisge que implemente uma certa interface java. Ou seja, sempre o controller tem uma forma de “ler” o modelo ou intrpretar certa informação como sendo o modelo. Essa forma de leitura é o contrato. O contrato é aquilo que se espera do objeto para que controller possa comunicar com ele. Este contrato, seja implicito ou explicito na forma de uma interface java ou uma classe abstrata sempre pertence no andar da apresentação.
Como eu implementaria uma interface sem que o objeto que a implementa estivesse na mesma camada ? Existem formas para isso ?
Sim, existem. A mais simples é o padrão Proxy, mas no caso do java este exige algum tipo de interface fisica. Um contrato conceptual não é suficiente.
Mas temos o padrão bridge que vai mais além e permite o desacoplamento entre a implementação e contrato de uso. O JDBC é todo baseado nisto. Ha uma definição rigorosa de como o driver dever responder, mas não como. Ou seja, o vendedor de bando de dados pode implementar o driver como quiser remoto ou local, como quiser, mas ele tem que responder às interfaces e contratos JDBC tal como explicitado na especificação JDBC. Tudo bem, que o JDBC não tem nada que ver com MVC, mas estamos de implementar uma interface de forma que a implementação fique em outra camada. Na maioria dos casos é incomum e até inutil usar uma camada diferente para a implementação é mais mais facil usar um adapter ou um business delegator, mas a tecnologia não nos impede de separar.
Portanto, no caso geral a implementação pode estar em outra camada, embora isso não seja nada comum ou útil. O Seam é uma tecnologia onde isso se torna comum e até quase que padrão, contudo isso limita , e muito, a evolução do sistema já que o Seam viola alguns principios basicos em nome da velocidade de desenvolvimento. Isto é bom no primeiro dia, mas pode ser um pesadelo no ultimo.
O model é onde o programador dá “inteligencia” a um robot automático que é o controlador. Essa inteligencia tende a mudar muito ao longo da vida do software e portanto não é bom misturar com outras coisas. Se quiserem de uma forma bem simples de memorizar : lógica de tela não se mistura com lógica de negocio. Não são a mesma coisa.
Espero que tenha esclarecido algo.
Muito boa complementação da conversa do outro post.