Galera, estou com uma duvida aqui e costaria da ajuda de vcs.
Em um projeto novo que estou trabalhando resolvemos usar o padrão active record e domain model.
Criamos uma classe chamada BasicActiveRecord que implementa os metodos salvar, excluir, alterar e buscarPorId. Todas as classes de negócio estendem desta classe e portanto todas as classes de negócio sabem se persistir.
Aqui começa a minha duvida. Como eu faço quando tiver que alterar dados de duas classes que não tem nenhum tipo de relacionamento e isso tiver que ser feito dentro de uma transação? Quem vai ser responsável por iniciar a transação, invocar os métodos de negócio das classes, verificar se houver alguma violação das regras e dar o commit ou o rollback?
Alguma dica?
Acho que vc deve delegar p/ alguem fazer isso. Criar um objeto que vai receber seus objetos e controlar isso p/ vc. Acredito que os objetos persistentes não devem conhecer essa responsabilidade. Vc continua chamando os metodos save dos objetos, mas dentro de um outro obj que vai controlar a transação.
É o que consigo pensar agora.
[quote=llvaleriano]Galera, estou com uma duvida aqui e costaria da ajuda de vcs.
Em um projeto novo que estou trabalhando resolvemos usar o padrão active record e domain model.
Criamos uma classe chamada BasicActiveRecord que implementa os metodos salvar, excluir, alterar e buscarPorId. Todas as classes de negócio estendem desta classe e portanto todas as classes de negócio sabem se persistir.
Aqui começa a minha duvida. Como eu faço quando tiver que alterar dados de duas classes que não tem nenhum tipo de relacionamento e isso tiver que ser feito dentro de uma transação? Quem vai ser responsável por iniciar a transação, invocar os métodos de negócio das classes, verificar se houver alguma violação das regras e dar o commit ou o rollback?
Alguma dica?
valeu.[/quote]
Existe um padrão chamado WorkUnit para resolver isso. Mas ActiveRecord não foi feito para usar em transações. É melhor DataMapper ou Store
Esse projeto tem pretensão de crescer muito? Active Record em Java sempre fica bem estranho quando o número de classes começa a crescer. E se o projeto for ter lógica de acesso a dados com alguma complexidade, o Active Record vira uma grande confusão.
Na teoria e nos exemplos, fica bem bonitinho, mas no mundo real, fica bem fedorento.
Sobre as transações, você pode usar interceptadores/filtros (WebWork, Tomcat) ou AOP (Spring…). Resolve muito bem o problema.
O projeto não é muito grande não, mas tem muita complexidade nas regras de negócio. A principio não irá crescer muito além do escopo que já foi definido, mas nada impede que isso aconteça.
O problema de usar filtros é que amarro a implementação de uma regra da camada de modelo com a requisição http. Se precisar criar uma nova visão q não seja web isso pode gerar problemas.
[quote=llvaleriano]O projeto não é muito grande não, mas tem muita complexidade nas regras de negócio. A principio não irá crescer muito além do escopo que já foi definido, mas nada impede que isso aconteça.
O problema de usar filtros é que amarro a implementação de uma regra da camada de modelo com a requisição http. Se precisar criar uma nova visão q não seja web isso pode gerar problemas. [/quote]
Nesse caso use WorkUnit. Sem saber como vc faz a persitencia é o máximo que se pode dizer.
O projeto ainda está na fase de elaboração, e a arquitetura está sendo definida. Ainda há tempo de se mudar de estratégia.
Neste caso, qual seria mais indicada?
Já sabemos que vamos modelar de acordo com o padrão Domain Model, e para alguns casos de uso, existe uma lógica de negócio com um nivel médio de complexidade (na maior parte do tempo temos que verificar o estado de alguns objetos e verificar se algumas operações podem ser executadas).
Qual seria a melhor alternativa, data mapper ou unit of work?
[quote=llvaleriano]O projeto ainda está na fase de elaboração, e a arquitetura está sendo definida. Ainda há tempo de se mudar de estratégia.
Neste caso, qual seria mais indicada?
Já sabemos que vamos modelar de acordo com o padrão Domain Model, e para alguns casos de uso, existe uma lógica de negócio com um nivel médio de complexidade (na maior parte do tempo temos que verificar o estado de alguns objetos e verificar se algumas operações podem ser executadas).
Qual seria a melhor alternativa, data mapper ou unit of work?
[/quote]
Domain Model é muito bonito na teoria, mas na prática são outros 500…
Se vc pode mudar a arquitetura então opte por JPA que lhe permite fazer tudo isso facilmente. Ele já tem um data mapper embutido e as transações vc pode controlar explicitamente.
Mas como fica a distribuição deste modelo em camadas?
Não tenho experiencia com jpa, só fiz alguns mapeamentos usando annotations para experimentar a novidade.
Qual seria o caminho das pedras?
Tenho minhas classes de negócio modeladas, vou fazer o mapeamento destas classes usando hibernate annotations.
Imagino que iremos usar uma fachada para centralizar/simplicar as chamadas aos métodos que estão programados nas classes de negócio. As chamadas para a fachada serão feitas em actions do struts.
A duvida é: Onde vai ficar o controle das transações? quem será responsável por persistir os dados?
[quote=llvaleriano]Mas como fica a distribuição deste modelo em camadas?
Não tenho experiencia com jpa, só fiz alguns mapeamentos usando annotations para experimentar a novidade.
Qual seria o caminho das pedras?
Tenho minhas classes de negócio modeladas, vou fazer o mapeamento destas classes usando hibernate annotations.
Imagino que iremos usar uma fachada para centralizar/simplicar as chamadas aos métodos que estão programados nas classes de negócio. As chamadas para a fachada serão feitas em actions do struts.
A duvida é: Onde vai ficar o controle das transações? quem será responsável por persistir os dados?
Valeu[/quote]
Pera ai! façade com domain model ? Ou bem que usa um ou bem que usa o outro. Se vc já abandonou a ideia do domain model, ok , mas se não, parece que tá havendo uma confusão ai.
A estrutura padrão para camadas é:
Apresentação : Command e BusinessDelegate (passa instruções ao servidor)
Controle : WorkUnit (controla inicio/fim da transação)
Modelo : Domain Model (as classes normais com anotações)
Persistencia: DAO (implementado de forma a suportar transações ad doc e mapeamento do Domain Model)
As actions são comand businessdelegate e workunit ao mesmo tempo.
As classes devidamente anotadas são o domain model. O JPA ou o Hibernate são o DAO.
Sergio, gostaria muito de conversar mais sobre esse assunto contigo.
Tem como vc adicionar meu contato no msn pra a gente poder ter uma conversa um pouco mais dinamica? Depois eu posto a conversa aqui no guj.
Deixa eu explicar melhor então, já que parece que tá havendo confusão.
Esta fachada, ao meu ver, pode sim ser usada junto com domain model. A fachada apenas abstrai o fluxo de iterações necessárias para realizar uma determinada função do sistema. Ela não executa nenhuma regra, apenas centraliza as chamadas para os objetos de dominio que possuem tais regras. É o que Martin Fowler chama de service layer.
[quote=llvaleriano]Deixa eu explicar melhor então, já que parece que tá havendo confusão.
Esta fachada, ao meu ver, pode sim ser usada junto com domain model. A fachada apenas abstrai o fluxo de iterações necessárias para realizar uma determinada função do sistema. Ela não executa nenhuma regra, apenas centraliza as chamadas para os objetos de dominio que possuem tais regras. É o que Martin Fowler chama de service layer.
Algum problema nesta implementação?
[/quote]
Então chame pelo nome certo Service Layer não é a mesma coisa que Façade … mas isso são detalhes. A questão que me levou à pergunta não tme a ver com nome mas com a inclusão de uma camada extra
Eu tinha entendido que vc ia usar actions do struts e domain model , nesse caso a lógia dentro do action é assim
Pedido p = ... // obtém pedido através do action form etc etc
p.fatura();
Service seria assim
// dentro do action
Service s = .. //obtém serviço
Pedido p = .. // obtém pedido da mesma forma que antes
s.fatura (p);
// dentro do service
public void fatura (Pedido p ){
p.fatura();
}
Veja que com Domain Model as operações estão nos objetos e portanto, se o ambiente não é destribuido (web não é, e struts é web) não ha necessidade de service. Que service vc está imaginando que não cabe dentro de um dos objetos do dominio ? Com qual finalidade vc usaria façade/service ?