Por que precisamos de estruturas para injeção de dependência? [fechadas]

42

Estive lendo mais sobre o princípio da Inversão de Controle e Injeção de Dependências como uma implementação e tenho certeza de que entendi.

Parece estar basicamente dizendo 'não declare as instanciações de seus alunos dentro da classe'. Em vez disso, as instanciações devem ser passadas e atribuídas pelo construtor; 'injetado' na classe a partir de uma fonte externa.

Se é simples assim, o que parece ser, por que precisamos de estruturas como primavera ou truque que implementam isso com anotações? Estou perdendo algo fundamental aqui? Estou realmente lutando para entender qual é o uso das estruturas de injeção de dependência.

Edit: Sobre a possível duplicata, acredito que minha pergunta é mais exclusiva, pois está perguntando sobre estruturas de DI em geral, não apenas no Spring. O Spring não é apenas uma estrutura de DI, por isso há muitas razões pelas quais alguém gostaria de usar o Spring que não está relacionado ao DI.

timsworth
fonte
11
Eles são úteis para transferir erros para o tempo de execução, em vez do tempo de compilação.
Den
1
@den Por que queremos fazer isso? Isso parece violar a falha rapidamente
ESTE USUÁRIO PRECISA DE AJUDA

Respostas:

26

Não precisamos das estruturas. É totalmente possível implementar a injeção de dependência manualmente, mesmo para um projeto relativamente grande.

Por outro lado, o uso de uma estrutura facilita, particularmente uma baseada em anotações ou na detecção automática de dependências, pois simplifica o processo: se eu decidir que preciso de uma nova dependência em uma classe, tudo o que preciso fazer é adicionar para o construtor (ou declarar um setter) e o objeto é injetado - não preciso alterar nenhum código de instanciação.

Além disso, as estruturas geralmente contêm outras funcionalidades úteis. O Spring, por exemplo, contém uma estrutura útil para programação orientada a aspectos, incluindo demarcação de transação declarativa (que é extremamente útil) e uma variedade de implementações de adaptadores que facilitam a integração de muitas bibliotecas de terceiros.

Jules
fonte
8
Bater o prego na cabeça. Nós não precisamos deles. Eles apenas facilitam a vida de grandes projetos. Honestamente, acho que as estruturas são mais complicadas do que valem para projetos menores. Encorajo o OP a não confundir a Injeção de Dependência com as estruturas que o suportam.
RubberDuck
1
bem dito. E por que reinventar a roda quando alguém já fez uma que já é boa e redonda?
jwenting
Exatamente isso. Exceto I não precisa alterar qualquer código instanciação - é claro, não há nenhum código instanciação ;-)
Mathieu Guindon
Parece que suas bibliotecas de DI são péssimas. Os bons podem adivinhar a classe para instanciar usando a reflexão.
Florian Margaine
2
qualquer pessoa que use reflexão para processamento em tempo de execução está fazendo errado. A reflexão é uma daquelas tecnologias que, só porque você pode fazer algo, não significa que deveria.
Gbjbaanb
12
  1. Por que precisamos de DI (Injeção de Dependência)?

    O mecanismo DI separa a produção e o consumo de objetos. As dependências de que um objeto precisa são entregues de forma transparente a partir do exterior. A vantagem do mecanismo é clara: você pode trocar as dependências a qualquer momento, por exemplo, usando um Objeto Nulo para fins de teste.

  2. Como isso é feito?

    Existem várias maneiras de atingir o objetivo:

    • Injetando dependências via injeção de construtor
    • Injeção via getter / setter
    • Injeção de interface
  3. Precisamos de estruturas de DI?

    Não. Não mesmo. Você pode simplesmente passar todas as instâncias para outros objetos manualmente. Se você tem uma aplicação pequena, não há necessidade de um contêiner de mola.

    Por outro lado, as estruturas oferecem uma ajuda, gerenciando objetos:

    • Eles ajudam a conectar relacionamentos complexos de objetos. Você não deve escrever nenhum código padrão, para gerar instâncias e passá-las para os objetos apropriados

    • Eles ajudam a controlar quando um objeto é criado: você pode criar instâncias durante a inicialização do aplicativo, mas em alguns casos uma criação lenta - somente quando necessário - é melhor

    • Eles ajudam a controlar quantas instâncias são criadas: uma por vida útil do aplicativo ou uma por solicitação (caso você esteja fazendo programação na web)

Se você projeta um tamanho apropriado - se sente a necessidade de escrever menos código padrão -, faz totalmente sentido usar uma estrutura (DI-). Existem mais prós do que contras.

Thomas Junk
fonte
2
Você pode usar bibliotecas de DI sem usar uma estrutura.
Florian Margaine
5

Com a primavera, é principalmente uma questão de conveniência.

Se você possui uma classe TopLevelque é constrói uma classe MiddleLevelque constrói uma classe LowLevele percebe que precisa de um novo parâmetro de construtor LowLevel, também é necessário adicioná-lo a TopLevele para MiddleLevelsimplesmente para que, quando for a hora de MiddleLevelconstruir um, LowLevelo valor esteja disponível para que possa ser passado ao seu construtor. Com a primavera, você apenas adiciona uma anotação.

Além disso, com o spring, é possível definir as dependências em um arquivo de configuração externo, em vez do xml, e isso supostamente permite gerar um novo sistema com uma fiação totalmente diferente "sem alterar nenhum código". (IMHO, isso é completamente mal direcionado, porque alterar xml não é muito diferente de alterar código e, na verdade, o código geralmente tem uma verificação de erro e verificação de tipo muito melhor do que xml.)

Outra coisa é que muitas pessoas têm medo de construtores; eles não os entendem, não gostam deles, preferem não usá-los.

Mike Nakis
fonte
3
Concordo principalmente, especialmente com a observação XML. IMHO, ter medo de construtores é provavelmente um mau motivo para usar uma estrutura de DI.
Robert Harvey
2
IMHO, ter medo de construtores é uma boa razão para ficar longe da programação. C -: =
Mike Nakis
5
Mas como isso é uma vantagem sobre uma fábrica (estática ou não)? (Que tem a vantagem de ser uma opção que você pode usar como apropriado enquanto que Primavera parece ser um tudo ou nada afair)
Richard Tingle
O @RichardTingle Spring pode representar uma vantagem principalmente devido a todas as outras coisas que ele faz além do DI, porque obviamente você pode alcançá-lo de muitas outras maneiras, sendo as fábricas estáticas. (Uma das menos legais, mas ainda assim.) Mas o que a pergunta é é se é necessário usar a mola para obter o DI, e é isso que eu tenho tentado responder: basicamente, não é necessário, apenas uma conveniência .
Mike Nakis
Este é um exemplo do que DI não é. 'Nível Superior' não deve criar MiddleLevel, mas deve recebê-lo ao construir TopLevelcomo argumento para o construtor. Da mesma forma MiddleLeveldeve receber um LowLevelem seu construtor.
Clearer
1

Alguns anos atrás, escrevi um programa para monitorar páginas da Web, portlets da Web e até mesmo determinadas tabelas de banco de dados em uma empresa na qual eu costumava trabalhar. Queria que fosse flexível o suficiente para que o usuário pudesse especificar quais monitores seriam executados e com quais parâmetros (URLs, logins, critérios de sucesso etc.). Então, eu escrevi para ler um arquivo XML e usar a reflexão Java para instanciar as classes especificadas e usar métodos setter para definir os parâmetros especificados.

Mais tarde, descobri que o Spring fará a mesma coisa por você e muito mais.

Então, no meu caso, descobri que

  1. O uso de uma estrutura de injeção de dependência ajuda a tornar o programa flexível e facilita a especificação de como ele funcionará (dentro de parâmetros bem definidos, é claro).

  2. O uso de uma estrutura DI de terceiros evita que você tenha que reinventar a roda.

Paul J Abernathy
fonte
4
Você poderia explicar mais sobre por que definir qual classe concreta usar é melhor dentro de um xml do que dentro de um arquivo java. Essa é a coisa que eu nunca entendi.
Richard Tingle
1
Não é uma bala mágica, mas uma vantagem do uso de arquivos de configuração é que, pelo menos em teoria, eles são mais fáceis de editar que o código. Além disso, eles podem ser alterados por um usuário que está executando seu programa, mas não tem acesso ao seu código-fonte. No exemplo que eu dei do meu programa bruto de injeção de dependência, algumas vezes eu alterava o arquivo de configuração XML para poder alterar a forma como o programa era executado, apesar de ter sido quem o escreveu. Se você não precisa da configurabilidade externa, pode ser mais fácil fazê-lo com código. Eu tive outro trabalho em que fizemos todo o DI no código e funcionou bem.
Paul J Abernathy