Informacao Basica sobre Arquitetura EE

Ola Pessoal,
Gostaria de ter uma informação/sugestão sobre um “probleminha” que eu me deparei,

Estou fazendo uma aplicação que de principio , vai apenas exibir relatórios de informações adquiridas no banco.
foi decidido que seria usado JSF como interface ( no caso a que iria obter os parametros ) e JPA/HIbernate Persistencia ( no momento so consulta)
Em meio a algumas pesquisas, leituras que fiz, vi que seria mais util utilizar um container (JBoss) com EJB (@Stateless - session) para gerenciar toda a questão do meu PersistencContext / transacao / etc…

Consegui fazer o meu projeto acontecer…
criei um projeto EJB-Module ( no qual chamei de Business ), onde esse teria as minhas Entity, classes de negocio…
criei um outro projeto EJB-MOdule ( no qual chamei de Facades ), onde esse apenas trataria a questão de fazer a comunicação entre o Client (View / JSF) e passar as informacoes para o Business.
criei um outro projeto “View” do tipo Dynamic WEB, no qual eu uso o JSF
disse ao Eclipse que o Facades dependia do projeto Business ( questão de class-path, lib… ) e que View dependia de Facades
até aqui tudo bem…

Eis a minha dificuldade,
Digamos que eu tenha la em meio as minha classes de dominio a classe Cliente ( que seria um entity … )
e eu queria listar esses clientes na minha VIEW, para que eu podesse passar esse Objeto Cliente e ele fosse reconhecido na view eu teria de colocar no projeto VIEW a dependencia do BUsiness,senão ele não reconheceria a Classe Cliente, ae pergunto a vocês isso é correto / possível ? ( se eu não estiver enganado, me parece que não se pode passar tais objetos para fora do “container EJB” - ex. saindo do facades e chegando na view )
como esse tipo de coisas deve ser feito ?
é o mesmo caso quando eu queria por exemplo preencher um combo com objetos… e etc

gostaria de ter a informação de vocês quanto a questão dessa arquitetura , creio que seja algo comum entre vocês…

Abraços,

Olá sudeval;

Sou Arquiteto JAVA de um empresa publica no Paraná. Nesta empresa estamos trabalhando com a arquitetura semelhante a sua, JBOSS, JPA/Hibernate Annotations e EJB3 na camada business e na camada View Strut2. No entanto não criamos a dependencia de projeto, pois os programadores trabalham de forma independente, para isso temos que gerar um JAR com as *.class de business (as Entity) e colocar no projeto WEB.

Os EJB3 são distribuídos e trabalham como provedores de Serviço, ou seja, coletam os dados, fazem consultas e manutenções diversas nos Objetos/Entitys, retornando para a View. Dentro do projeto EJB3 temos a FACADE, esta esta anotada com @Statless, e faz acesso a camada DAO (alguns dizem que com o EJB3 a camada DAO morreria, mas temos querys complexas e se faz necessário).

Diante disso, quando fazemos um relatório, a controladora do Struts2 aciona o EJB3 solicitando a ele uma Collection do tipo Cliente, por exemplo, e retonando esta coleção, ou seja , o objeto de negócio é o MESMO seja na camada VIEW quanto na camada de negócio.

No seu caso, a modificação que faria, seria um EJB3 (um Projeto) com a sua Interface e esta interface com todos os métodos declarados. Dentro do EJB, ele faria todo o processamento e retornaria o PROPRIO Objeto para a camada VIEW.

Bom, acho que é isso, qualquer duvida escreve ai.

t+

Simples e direto ao ponto:

  1. Use ant para gerenciar projetos. Vai salvar a sua vida no futuro :wink:
  2. Isole as suas classes de entidade em um único projeto. Isole as interfaces de DAO, business facade, controller em projetos distintos também.
  3. Crie projetos (ant!) para as implementações destas interfaces, para cada camada. Exemplo:

Projetos:

  • domain.jar
  • dao.jar
  • dao-impl.jar
  • facade.jar
  • facade-impl.jar
  • controller.jar
  • controller-impl.jar
  1. Crie os projetos das camadas clientes conforme necessário. Pode ser uma aplicação web, um cliente desktop, um cliente mobile, etc…

Por quê fazer isso tudo?

Na minha experiência como arquiteto, descobri que projetos crescem, fogem ao controle dos arquitetos rapidinho :wink: O que começa “pequeno e simples” geralmente cresce em número de requisitos, usuários concorrentes, número de interfaces clientes, etc. Então, o único jeito de se “defender” disso tudo é modularizar a sua arquitetura. Se você olhar o meu exemplo (e conhecer um pouquinho de Ant), vai perceber que é possível “empacotar” um arquivo EAR com diferentes implementações para diferentes necessidades/clientes. Ou personalizar alguns componentes de cada camada de acordo com diferentes necessidades (possivelmente, de diferentes clientes).

Se o seu projeto é realmente simples, fazer tudo que eu descrevi pode ser overkill. Mas avalie muito bem se esse é mesmo o caso. Porque se não for… quanto antes você tiver uma arquitetura assim, flexível e bem organizada, melhor.

Espero ter ajudado!

Rodrigo

uhm! compreendi e agradeço…
me diz uma coisa, o fato de eu sair modularizando a aplicação como você citou ae, pegando o seu exemplo , era possivel eu passar Objetos do domain.jar entre todas as camadas inclusive chegando na view ? ( uso de ejb ali por facades e controller )

abraços

Sim, porque provavelmente você vai tornar o domain.jar uma dependência das demais camadas. O importante aqui é que o projeto domain não dependa de ninguém - para que você possa reaproveitá-lo em quaisquer outros projetos.

As dependências entre as camadas fica mais ou menos assim:

  • Todos os projetos dependem de "domain"
  • Domain <- DAO <- Facade <- Controller <- View

Ah… para não gerar polêmica, deixo claro que esta talvez não seja a "maneira mais correta e cool" de fazer as coisas… É só o jeito que eu faço, foi assim que eu aprendi a fazer, e para mim funciona muito bem, obrigado :wink:

Rodrigo

javaBeats, como tu gerencia as versões de tanto jars?
Exemplo, mexeu no domain.jar e este vai ter que ser copiado para todos esses outros projetos. Maven?

Não… eu uso só o SVN e o Ant :stuck_out_tongue:

Os usuários aqui têm permissões restritas sobre o que podem alterar. Essas versões são congeladas no SVN, alterações nelas passam por um processo definido aqui. O que pode de fato ser alterado com mais liberdade é gerenciado via branches e uso de timestamps de build dos componentes. E aí, versionamento deles, liberação p/ QA, etc… até atualização em produção.

Rodrigo

Digo, com tanto projeto e jars, como tu distribui os jars nos projetos que dependem deles?
Você deve estar comitando o jar no svn? Dai sai uma nova versão de um jar tem que ir de projeto em projeto e atualizar?

Não. Eu tenho outro projeto “guarda-chuva”, que nós chamamos de “deployer”, com scripts ant para deploy da aplicação com diferentes customizações. Esse projeto reúne também as dependências (jars), internas e externas. Ao atualizar o repositório de dependências deste projeto (disponível também no SVN), o desenvolvedor tem as dependências atualizadas para trabalhar em seus projetos específicos.

Aliás, já que você tocou no assunto, aposto que o Maven seria uma ótima ferramenta para gerenciar isso tudo - talvez de forma mais eficaz e mais simples, certamente. Entretanto, é com Ant que tudo está estruturado hoje. Eu teria de estudar e planejar uma migração para isso :smiley:

[quote=fabiofalci]Digo, com tanto projeto e jars, como tu distribui os jars nos projetos que dependem deles?
Você deve estar comitando o jar no svn? Dai sai uma nova versão de um jar tem que ir de projeto em projeto e atualizar?[/quote]

Não sei como ele faz, mas uma opção é colocar os jars em uma shared library no servidor de aplicações, assim tudo ficaria centralizado.

Pois é, eu cheguei a usar o maven, mas o plugin do eclipse era tão ruim que desisti.
Então comecei a estudar o ivy
http://ant.apache.org/ivy/

Gostei, ele é apenas um gerenciador de dependencia e tem um boa integração com o ant.

Lembrando que numa aplicação JEE, segundo a JCP.

Precisamos dos seguintes cargos/responsabilidades:

Application Component Deployer
Application Assembler
Deployer
System Administrator
*Toll Provider
*Product Provider

Sendo que normalmente todas essas tarefas ficam a cargo da equipe porém não dividida, ou seja, todos fazem tudo. Se esses processos de implantação e implementação também fosse modularizados e não só o sistema (código) teriamos uma maneira muito melhor de controlar o projeto e não só as versões de cada jar (o que nesse contexto seria algo até pobre de se fazer.)

[quote=sudeval]Ola Pessoal,
Gostaria de ter uma informação/sugestão sobre um “probleminha” que eu me deparei,

Estou fazendo uma aplicação que de principio , vai apenas exibir relatórios de informações adquiridas no banco.
foi decidido que seria usado JSF como interface ( no caso a que iria obter os parametros ) e JPA/HIbernate Persistencia ( no momento so consulta)
Em meio a algumas pesquisas, leituras que fiz, vi que seria mais util utilizar um container (JBoss) com EJB (@Stateless - session) para gerenciar toda a questão do meu PersistencContext / transacao / etc…

Consegui fazer o meu projeto acontecer…
criei um projeto EJB-Module ( no qual chamei de Business ), onde esse teria as minhas Entity, classes de negocio…
criei um outro projeto EJB-MOdule ( no qual chamei de Facades ), onde esse apenas trataria a questão de fazer a comunicação entre o Client (View / JSF) e passar as informacoes para o Business.
criei um outro projeto “View” do tipo Dynamic WEB, no qual eu uso o JSF
disse ao Eclipse que o Facades dependia do projeto Business ( questão de class-path, lib… ) e que View dependia de Facades
até aqui tudo bem…

Eis a minha dificuldade,
Digamos que eu tenha la em meio as minha classes de dominio a classe Cliente ( que seria um entity … )
e eu queria listar esses clientes na minha VIEW, para que eu podesse passar esse Objeto Cliente e ele fosse reconhecido na view eu teria de colocar no projeto VIEW a dependencia do BUsiness,senão ele não reconheceria a Classe Cliente, ae pergunto a vocês isso é correto / possível ? ( se eu não estiver enganado, me parece que não se pode passar tais objetos para fora do “container EJB” - ex. saindo do facades e chegando na view )
como esse tipo de coisas deve ser feito ?
é o mesmo caso quando eu queria por exemplo preencher um combo com objetos… e etc

gostaria de ter a informação de vocês quanto a questão dessa arquitetura , creio que seja algo comum entre vocês…

Abraços,
[/quote]

1 - Pq você não utilizou o padrão Business Delegate para desacoplar as camadas, ao invés de criar um novo projeto EJB? http://www.developer.com/java/ent/article.php/3625646

2 - O padrão DTO, mesmo que sendo considerado um anti-pattern, ainda é necessário em alguns casos, mesmo com EJB3, claro que o uso de frameworks como o SEAM removeria esta dependência.


Cara, empacote todas as classes do projeto em um único jar, ou que isso seja feito no momento da distribuição para outros sistemas que dependem dele, pois segmentar os jars por camadas (domain, controller, dao e etc…) trará problemas de distribuição/versões quando existem mais sistemas envolvidos. Digo isso por experiência própria pois cada equipe de sistema vive em um tempo de evolução diferente, e controlar a versão 1.0 que voce distribuiu para aplicacao X, a 1.1 para a Y e etc… vai lhe dar muita dor de cabeça, isso a principio é inevitável a não ser que todos os sistemas façam atualizações (releases) em conjunto… e se isso for feito com vários jars por camada, vai ser muito mais trabalhoso. Pode ser que a tentativa de gerenciar esse deployment via ant/maven possa facilitar essa tarefa.

abracos,

Apenas complementando, para evitar problemas de versão utilize shared libraries, neste caso todos os jars seriam gerenciados em um unico lugar, o servidor.

opa pessoal , nesse projeto segui as dicas de vcs e deu tudo certo…

Agora to com um caso um pouco diferente ( pra mais complexo ).

Como que vcs fazem a comunicação entre dois projetos distintos EJB, digamos que eu tenha um sistema de autenticacao de usuários e um outro(s) ( vai ser mais de um ) sistema qualquer que vá utilizar esse projeto, digamos um sistema de Farmacia, onde ao se acessar o sistema de farmacia a questão de autenticar o usuario/senha passado seja usado o sistema de autenticacao.

isso faz com que no projeto de Farmacia tenha a dependencia do projeto de autenticacao, aqui eu uso o InitialContext e faco um lookup para achar a classe de sessao do projeto de autenticacao, ae entra o X da questão, aqui ocorre algo como o meu 1o problema ae, com relacao a dependencias…
se eu nao colocar a lib dentro do projeto(embora no deploy eu tenha usado ela como dependencia), vai dar um erro em tempo de execucao com o ClassNotFoundExeption… ( fiz isso pra teste pq houvir falar que se tivesse dentro do mesmo container ele iria prover isso… )
esse ae como é necessário essa lib, eu devo utilizar um local para shared library que é o ideial ne, ou estou fazendo algo errado ae ?

tenho algo com esse erro aqui
http://www.guj.com.br/posts/list/88997.java