Injeção de dependência em classes do domínio
27/04/2008 00:00
0
No Grails, é possível injetar services em classes do domínio (por autowiring). Mas é também possível injetar classes de domínio em outras classes de domínio?

Por exemplo, imagine que eu tenha uma classe Book:

class Book {
def specification

// outros métodos e atributos...
}


Digamos que eu precise injetar um objeto specification em cada Book que for instanciado. Digamos, ainda, que esse objeto specification a ser injetado implemente alguma interface da qual Book dependa (um método isSpecifiedBy(something), por exemplo).

class Specification1 {
def isSpecifiedBy(something){
// alguma implementação
}
}

class Specification2 {
def isSpecifiedBy(something){
// outra implementação
}
}


O que eu gostaria de fazer é declarar esse specification naquele arquivo de contexto do Spring, de modo a definir qual implementação dessa interface os objetos Book iriam utilizar, já que eu poderia ter várias implementações dessa interface.

Eu sei que posso fazer isso com uma factory, mas o design ficaria bem mais elegante com injeção de dependência, do mesmo modo como acontece com os services...

Obrigado.
Tags: Grails


0
É possivel sim injetar beans nas classes de dominios. Procure no manual por "dependency injection and domain classes".

valeuz...


0
Acho que me expliquei mal...

O manual (e todas as outras referências que encontrei) mostra como injetar serviços em outras classes, sejam elas classes de domínio ou outros serviços.

Ao instanciar um objeto do domínio, se esse objeto possuir um atributo chamado <alguma coisa>Service, o Grails procura uma classe de serviço com o mesmo nome e injeta o seu singleton nesse objeto do domínio. É o que o Spring chama de &quot;autowiring by name&quot;.

Usando um exemplo do manual:

class Book &#123;	

def bookService
def buyBook() &#123;
bookService.buyBook(this)
&#125;
&#125;


Como a classe Book possui um atributo chamado bookService, o Grails procurará uma classe chamada BookService e injetará a instância dessa classe em cada objeto Book que for criado.

Eu gostaria desse mesmo comportamento, mas com outras classes de domínio e não somente services. Isso é importante porque estou procurando deixar toda a lógica de negócios dentro das classes de domínio. E às vezes, é preciso injetar um objeto do domínio dentro de outro objeto do domínio.[/code]
28/04/2008 00:00


0
Entendi agora, mas veja, não faz muito sentido usar DI nesse caso. É bem mais interessante que a logica/relacionamento entre suas classes de domínio fique explicita.

Pode dar um exemplo de código do que vc quer fazer?

valeuz...


0
Os detalhes são os seguintes: estou desenvolvendo um sistema para o domínio de transporte público urbano. Nesse domínio, existem passageiros, que podem estar associados a várias categorias (&quot;idoso&quot;, &quot;estudante&quot;, etc).

Um dos requisitos é que o sistema deve informar, para um dado passageiro, quais são as categorias que lhe são permitidas. Por exemplo, um passageiro associado à categoria &quot;estudante&quot; poderia ser associado também à categoria &quot;trabalhador&quot;, mas não à categoria &quot;idoso&quot;.

Agora imagine que possam existir outras regras para esse conjunto de categorias (um número máximo, por exemplo), de modo que eu possa simplesmente modificar um arquivo de configuração para trocar essa regra. Esse também é um dos requisitos. Já que o Grails oferece aquele resources.groovy, seria a opção perfeita.

A melhor solução que encontrei para esse problema de variabilidade das regras do domínio foi usar o padrão Specification. Dessa maneira, eu tenho uma classe Passageiro, com um método 'categoriasPermitidas()', que retorna uma lista. Para inferir essas categorias, ele usa uma especificação. Mas a classe Passageiro conhece apenas a interface da especificação, e não a sua implementação.

Para cada regra diferente de combinação de categorias, eu teria uma implementação diferente. A idéia é configurar na DSL do Spring qual implementação eu quero usar e essa implementação seria injetada nos objetos da classe Passageiro.

Mas tanto Passageiro, quanto as especificações são classes do domínio, que implementam regras de negócio. Por isso, a pergunta: como eu injeto uma especificação dentro de um Passageiro, sem usar factory, nem service locator, usando apenas DI?

Valeu!
02/05/2008 00:00


0
Bem, acabei descobrindo. E a solução estava na minha cara o tempo todo <!-- s:shock: --><img src="{SMILIES_PATH}/icon_eek.gif" alt=":shock:" title="Shocked" /><!-- s:shock: --> : sempre que uma classe de domínio é instanciada, se essa classe tiver um atributo cujo nome esteja declarado no resources.groovy, o Grails tenta injetar essa dependência no objeto recém-criado.

Ou seja, é o mesmo comportamento para serviços, controladores e classes de domínio
03/05/2008 00:00



Ainda não faz parte da comunidade???

Para se registrar, clique aqui.


Aprenda Groovy e Grails com a Formação itexto!

Newsletter Semana Groovy

Assinar

Envie seu link!


Livro de Grails


/dev/All

Os melhores blogs de TI (e em português) em um único lugar!

 
Creative Commons
RSS Grails Brasil é mantido por itexto Consultoria.
Em caso de problemas contacte Henrique Lobo Weissmann (Kico) por e-mail: kico@itexto.com.br
Todo o conteúdo presente neste site adota o Creative Commons como licença padrão.
Ver: 4.14.0
itexto