Discussão sobre arquitetura usando vraptor 3

19 respostas
N

Galera to fazendo um sistema utilizando o vraptor 3. Iniciei com uma abordagem e agora estou pensando em mudar, pois não estou gostando do rumo que a atual está seguindo. Normalmente quando desenvolvo sistemas web eu penso basicamente nas seguintes camadas:

Controller --> Service --> DAO

Imagino esse controller como sendo uma espécie de façade, onde simplesmente recebo os dados que vieram da interface, monto os objetos e passo para o Service validar e chamar os DAOs necessários para persistir os dados. Na aplicação que eu criei inicialmente achei que não iria precisar do Service, então criei apenas o DAO, e o anotei como @Component do vraptor, daí injetava os DAOs que eu precisasse no meu controller.

Uma coisa que está me incomodando é que toda a validação está sendo feita no próprio controller (está certo isso?), outra coisa é que o construtor do meu controller está ficando cheio de DAOs :slight_smile: eu imagino que uma camada de serviço me permitiria injetar apenas 1 Serviço e este se encarregaria de ter os DAOs/repository que fossem necessários.

Minha dúvida nesse caso é: Eu posso anotar essa classe de serviço também com o @Component? Ou seja, eu injetaria os DAOs nela e injetaria ela no meu controller. Gostaria de saber como vocês normalmente constroem a arquitetura de aplicações com vraptor 3, especialmente para aplicações médio e grande porte, que é o meu caso. Agradeço desde já a contribuição de todos.

19 Respostas

J

A meu ver o Controller, serve apenas para tratar validação dos dados no lado server. Por exemplo, na hora de verificar o formulário, ele verifica se todos os dados estão ok, antes de salvar no banco. Se passar pela validação do Controller, vai para a classe de Negócios, onde esses dados serão tratados e se necessário chamar os Daos.

Seria algo assim:

Controller -> Negócios (Aqui poderia ser um façade) -> Dao

Eu injetaria a regra de Negócios no Controller e os DAOs na classe de Negócios. É bem parecida com a sua estrutura, a única diferença é no código dentro do Controller, o Controller ao meu ver, só envia e recebe informação, no máximo faz uma validação básica de formulário. No meu caso uso Hibernate Validator e chamo ele dentro do Controller.

Assim ficaria um pouco melhor, porque validações comuns, ficariam separadas usando Hibernate Validator e mais específicas dentro do Controller, como por exemplo, em um formulário de upload, verificar se o usuário realmente enviou um arquivo ou se mandou o arquivo com a extensão que você deseja.

Espero ter ajudado. Vamos ver, como o resto do pessoal trabalha.

L

Voce está usando um único controller?

M

Sugiro utilizar o hibernate validator para as validações…e só chama ele no controller, a documentação do vraptor tem exemplos da utilização.

N

javablue:
A meu ver o Controller, serve apenas para tratar validação dos dados no lado server. Por exemplo, na hora de verificar o formulário, ele verifica se todos os dados estão ok, antes de salvar no banco. Se passar pela validação do Controller, vai para a classe de Negócios, onde esses dados serão tratados e se necessário chamar os Daos.

Seria algo assim:

Controller -> Negócios (Aqui poderia ser um façade) -> Dao

Eu injetaria a regra de Negócios no Controller e os DAOs na classe de Negócios. É bem parecida com a sua estrutura, a única diferença é no código dentro do Controller, o Controller ao meu ver, só envia e recebe informação, no máximo faz uma validação básica de formulário. No meu caso uso Hibernate Validator e chamo ele dentro do Controller.

Assim ficaria um pouco melhor, porque validações comuns, ficariam separadas usando Hibernate Validator e mais específicas dentro do Controller, como por exemplo, em um formulário de upload, verificar se o usuário realmente enviou um arquivo ou se mandou o arquivo com a extensão que você deseja.

Espero ter ajudado. Vamos ver, como o resto do pessoal trabalha.

Achei interessante a ideia de validação inicial no controller… ou seja, lá eu validaria coisas como obrigatoriedades, tipos do campo, tamanho etc… e deixaria as regras de negócio mesmo no serviço. Eu poderia fazer um misto então? Por exemplo, num crud simples, onde não existem regras de negócio, mas apenas validações como as que eu citei, eu poderia injetar o DAO diretamente no meu controller? Ou devo ser mais purista e sempre criar essa estrutura controller --> service --> dao?

E vocês acham necessário usar spring ou eu posso fazer como eu disse, anotar tanto o DAO como o Service com a @Component do vraptor?

J

nosbor84:
javablue:
A meu ver o Controller, serve apenas para tratar validação dos dados no lado server. Por exemplo, na hora de verificar o formulário, ele verifica se todos os dados estão ok, antes de salvar no banco. Se passar pela validação do Controller, vai para a classe de Negócios, onde esses dados serão tratados e se necessário chamar os Daos.

Seria algo assim:

Controller -> Negócios (Aqui poderia ser um façade) -> Dao

Eu injetaria a regra de Negócios no Controller e os DAOs na classe de Negócios. É bem parecida com a sua estrutura, a única diferença é no código dentro do Controller, o Controller ao meu ver, só envia e recebe informação, no máximo faz uma validação básica de formulário. No meu caso uso Hibernate Validator e chamo ele dentro do Controller.

Assim ficaria um pouco melhor, porque validações comuns, ficariam separadas usando Hibernate Validator e mais específicas dentro do Controller, como por exemplo, em um formulário de upload, verificar se o usuário realmente enviou um arquivo ou se mandou o arquivo com a extensão que você deseja.

Espero ter ajudado. Vamos ver, como o resto do pessoal trabalha.

Achei interessante a ideia de validação inicial no controller… ou seja, lá eu validaria coisas como obrigatoriedades, tipos do campo, tamanho etc… e deixaria as regras de negócio mesmo no serviço. Eu poderia fazer um misto então? Por exemplo, num crud simples, onde não existem regras de negócio, mas apenas validações como as que eu citei, eu poderia injetar o DAO diretamente no meu controller? Ou devo ser mais purista e sempre criar essa estrutura controller --> service --> dao?

E vocês acham necessário usar spring ou eu posso fazer como eu disse, anotar tanto o DAO como o Service com a @Component do vraptor?

Nesse caso eu sou mais purista. Porque essas classes de negócio podem ter outros métodos relativos ao crud, ou que podem vir a serem adicionados posteriormente. E desse jeito, sempre deixa o seu Controller mais limpo e com baixo acoplamento. Já que toda a regra estará em uma outra classe, caso você precise usar em outro lugar, não repetirá código.

[EDIT] O VRaptor usa o Spring dentro dele…então pode usar o @Component

Lucas_Cavalcanti

o DAO e o Service devem ser anotados com @Component sim, para você usar a injeção de dependências do VRaptor…

a abordagem de ter o Service só quando existem validações de negócio é razoável, e colocar as validações de modelo no, er, modelo. Criar um service que só delega tudo pros daos é meio ruim.

Eu costumo usar o Controller mesmo para fazer validação de negócios, mas só quando elas não são muito complicadas

L

Voces estão usando qual validator? do Vraptor, Hibernate Validator, Bean validator?

Ou ambos?

Lucas_Cavalcanti
validator.validate(objeto); // do VRaptor

que usa o BeanValidator/Hibernate validator e já integra ao vraptor

J

Lucas Cavalcanti:
validator.validate(objeto); // do VRaptor
que usa o BeanValidator/Hibernate validator e já integra ao vraptor

E funciona que é uma beleza viu ? rs

Fica muito produtivo.

P

nosbor84:
Galera to fazendo um sistema utilizando o vraptor 3. Iniciei com uma abordagem e agora estou pensando em mudar, pois não estou gostando do rumo que a atual está seguindo. Normalmente quando desenvolvo sistemas web eu penso basicamente nas seguintes camadas:

Controller --> Service --> DAO

Imagino esse controller como sendo uma espécie de façade, onde simplesmente recebo os dados que vieram da interface, monto os objetos e passo para o Service validar e chamar os DAOs necessários para persistir os dados. Na aplicação que eu criei inicialmente achei que não iria precisar do Service, então criei apenas o DAO, e o anotei como @Component do vraptor, daí injetava os DAOs que eu precisasse no meu controller.

Uma coisa que está me incomodando é que toda a validação está sendo feita no próprio controller (está certo isso?), outra coisa é que o construtor do meu controller está ficando cheio de DAOs :slight_smile: eu imagino que uma camada de serviço me permitiria injetar apenas 1 Serviço e este se encarregaria de ter os DAOs/repository que fossem necessários.

Minha dúvida nesse caso é: Eu posso anotar essa classe de serviço também com o @Component? Ou seja, eu injetaria os DAOs nela e injetaria ela no meu controller. Gostaria de saber como vocês normalmente constroem a arquitetura de aplicações com vraptor 3, especialmente para aplicações médio e grande porte, que é o meu caso. Agradeço desde já a contribuição de todos.

O que vi de vantagem de usar classes Service e separar as necessidades do vraptor da logica de negocio, amanhã se eu quiser mudar de framework aproveito as classes Service.

N

Até concordo em parte… só que o vraptor tem a vantagem de não ser um framework intrusivo. O meu controller é apenas uma classe java anotada, e com métodos que utilizam apenas objetos do meu negócio. Confesso que essa foi a característica do vraptor que mais me motivou a utilizá-lo. Até mesmo a validação é feita utilizando frameworks como Bean e HibernateValidator, e com baixo acoplamento.

Por isso inicialmente eu nem pensei em criar essa camada de serviço. O que tem me incomodado é apenas o fato de eu ter que injetar vários DAOs no meu controller, me preocupa também o fato de ele ficar muito verboso, o que pode tornar um problema futuramente. E aí, em termos práticos, vocês veem a real necessidade dessa camada de serviço?

J

nosbor84:
Até concordo em parte… só que o vraptor tem a vantagem de não ser um framework intrusivo. O meu controller é apenas uma classe java anotada, e com métodos que utilizam apenas objetos do meu negócio. Confesso que essa foi a característica do vraptor que mais me motivou a utilizá-lo. Até mesmo a validação é feita utilizando frameworks como Bean e HibernateValidator, e com baixo acoplamento.

Por isso inicialmente eu nem pensei em criar essa camada de serviço. O que tem me incomodado é apenas o fato de eu ter que injetar vários DAOs no meu controller, me preocupa também o fato de ele ficar muito verboso, o que pode tornar um problema futuramente. E aí, em termos práticos, vocês veem a real necessidade dessa camada de serviço?

Eu particularmente prefiro. Se não o controller, começa a ter validações, regras de negócios e ainda acesso aos DAOs. E até onde eu entendi, você quer fazer um único Controller né?

Se for isso, imagina a bagunça que ia ficar. E mesmo que não for, se você tiver uma tela complexa, ainda assim fica muita coisa misturada. Mas é aquela tal história, não existe bala de prata. Vai de cada um, eu prefiro manter tudo um pouco mais separado e organizado, até porque não é trabalho nenhum criar outra classe para ser esse serviço. Imagine que você vai fazer um webservice que necessite dessas lógicas, você vai mandar ele buscar a lógica no Controller? Estranho né?

Mas depende do projeto, você disse que o seu era médio e grande né? Então recomendo assim, é menos dor de cabeça no futuro eu acho. Em projetos de pequeno porte, não vejo problema em colocar algumas lógicas no controller.

N

Eu terei vários controllers, não 1 apenas… aí seria uma prática suicida…rs pelo menos no meu caso né… O problema que eu vejo, não é bem um problema mas um vislumbre da realidade…rs, é que eu terei vários Services que não fazem nada a não ser chamar o DAO, por isso falei na opção de mesclar e injetar o DAO em alguns controllers e serviços em outros… mas essa despadronização pode gerar confusão…

J

Então você tem que analisar o que é melhor. Será que realmente é só chamar Dao? Se for beleza.

Mas acho difícil…rs

As coisas sempre complicam, e eu prefiro um pouco mais normatizado. E deixo uma interface Service bonitinha caso precise usar em outro lugar, Web Service, Swing, ou-seja-lá-o-que-o-cliente-inventar. Rs

Mas falando sério…vai da sua análise, Custo X Benefício

Lucas_Cavalcanti

o fato de um controller precisar de muitos DAOs é uma dica de que esse controller está grande demais, e deveria ser quebrado em dois

N

Não é nem isso… é que esses DAOs são apenas pra preencher as combos da página (uf,municipio, e outras classes de negócio), mas acho que eu poderia fazer isso via ajax daí dava pra tirar a injeção desses DAOs.

P

nosbor84:
Até concordo em parte… só que o vraptor tem a vantagem de não ser um framework intrusivo. O meu controller é apenas uma classe java anotada, e com métodos que utilizam apenas objetos do meu negócio. Confesso que essa foi a característica do vraptor que mais me motivou a utilizá-lo. Até mesmo a validação é feita utilizando frameworks como Bean e HibernateValidator, e com baixo acoplamento.

Por isso inicialmente eu nem pensei em criar essa camada de serviço. O que tem me incomodado é apenas o fato de eu ter que injetar vários DAOs no meu controller, me preocupa também o fato de ele ficar muito verboso, o que pode tornar um problema futuramente. E aí, em termos práticos, vocês veem a real necessidade dessa camada de serviço?

Pra não ter que receber varios DAOs no meu contrutor criei um DaoFachada e recebo apenas ele.

leandronsp

ou pode utilizar o padrão factory. No construtor voce passa o DaoFactory e nos metodos faz chamada a factory.getXDao()

Daner

Também usei essa abordagem, criei um façade para os DAOs. Ficou claro e organizado, além de muito fácil de manter…

Criado 15 de junho de 2011
Ultima resposta 29 de dez. de 2011
Respostas 19
Participantes 8