DEV Community

Cover image for Injeção de dependência através de atributos é o ideal?
Thiago Lino
Thiago Lino

Posted on

Injeção de dependência através de atributos é o ideal?

No framework Spring quando queremos fazer alguma injeção de dependência (DI) é comum fazermos por atributos.

 @Autowired
 private InjectedDependency injectedDependency;
Enter fullscreen mode Exit fullscreen mode

Porém este método tem suas desvantagens e vou dizer quais.
Mas antes vamos escolher uma batida para acompanhar.

Agora sim.

Existem 3 maneiras de se realizar a injeção de dependência no Spring, apesar da documentação, no momento que escrevo, citar apenas duas. A já citada e exemplificada por atributo, através do construtor da classe e por setters métodos.

Pelo construtor:

private InjectedDependency injectedDependency;

@Autowired
public MyDependencyInjection(InjectedDependency injectedDependency) {
  this.injectedDependency = injectedDependency;
}
Enter fullscreen mode Exit fullscreen mode

E por setters:

private InjectedDependencyOne injectedDependencyOne;
private InjectedDependencyTwo injectedDependencyTwo;

@Autowired
private void setInjectedDependencyOne(InjectedDependencyOne injectedDependencyOne) {
  this.injectedDependencyOne = injectedDependencyOne;
}

@Autowired
private void setInjectedDependencyTwo(InjectedDependencyTwo injectedDependencyTwo) {
  this.injectedDependencyTwo = injectedDependencyTwo;
}
Enter fullscreen mode Exit fullscreen mode

A primeira vista realizar a injeção de dependência por atributos parece ser, e é, mais simples e menos verbosa. Uma linha e direto ao ponto(tirando a anotação). Porém nem sempre o simples é o melhor, eis os pontos negativos.

Não permite imutabilidade dos nossos atributos

Nossa injeção não funcionará com atributos da classe que forem declarados como final, logo perdemos a imutabilidade destes atributos. Com a injeção através dos construtores não perderiamos a imutabilidade destes atributos.

Ferir o S do SOLID

Adicionar dependências a nossa classe por atributos por ser menos verboso pode trazer o problema de nossa classe possuir várias dependências sem nos darmos conta que a classe esta fazendo mais do que deveria, tendo mais de uma responsabilidade ferindo o Single responsibility principle. A injeção através dos construtores nos ajudaria tornando este construtor cheio e mais visível da quantidade de dependências e responsabilidades da classe .
Aqui diria que é mais questão de dar visibilidade que uma refatoração pode ser necessária.

Esconde as dependências

A classe perde a responsabilidade por obter e gerenciar as dependências, deixando a cargo dos containers de injenção de dependência. Neste cenário seria ideal deixar claro, além de ser recomendável quando se usa DI, quais as dependências utilizadas são obrigatórias e quais são opcionais. O que ficaria inviável através de atributos. Utilizando construtores para obrigatórios e setters para opcionais conseguimos.

Acoplamento do container de DI

Como citado anteriormente a responsabilidade agora será dos containers de DI, neste caso containers Spring. O que deixa nosso desenvolvimento acoplado ao container.
Fora do container da aplicação fica mais dificíl utilizar estas dependências. Em um cenário de testes unitários por exemplo, seria necessário instanciar este Spring container(o que alteraria nosso teste unitário para um de integração) e utilizar reflexão para settar estes atributos.
Utilizando a DI com construtores invés de por atributos, apenas instanciamos estas classes e passamos como nossas dependências.

Conclusão

Realizar a injeção de dependência por construtores ou através de setters apesar de ser mais verboso deixa nosso código mais legível, na minha opinião.
Um dos exemplos seria quando temos um construtor com muito parâmetros, neste caso as dependências, indica que nossa classe faz mas do que deveria e pode caber uma refatoração. Ainda sobre ser tornar o código legível, podemos citar também sobre a obrigatoriedade de uma dependência quando passada através de construtores ou sua opcionalidade quando passada por setteres.

Se você achou que tem um ponto ou vários que não faz sentido comenta ae pra gente debater sobre, uma discussão saúdavel é ótimo para aprender.

Referências que usei

Top comments (0)