Upgrade to Pro — share decks privately, control downloads, hide ads and more …

[GOPHERCON LATAM 2025] Injeção de dependência e...

Sponsored · Your Podcast. Everywhere. Effortlessly. Share. Educate. Inspire. Entertain. You do you. We'll handle the rest.

[GOPHERCON LATAM 2025] Injeção de dependência em Go: Construindo código modular e sustentável

Palestra apresentada na Gophercon Latam em 2025.

Avatar for Vinítius Salomão

Vinítius Salomão

May 08, 2025
Tweet

Other Decks in Technology

Transcript

  1. Injeção de Dependência em Go Construindo código modular e sustentável

    05/05/2025 Andreia Camila Vinítius Salomão Senior Software Engineer Senior Staff Software Engineer
  2. CONTEÚDO Sobre nós 01 A Dor e o Abecedário Quando

    (não) Usar DI Do "Jenga" ao "Lego" Wire — “Compile!” Dig & Fx — “Reflita!” 02 03 04 05 06 Takeaways 07
  3. { Injeção de dependência (DI) é programar de forma que

    os recursos dos quais dependemos sejam abstrações.
  4. É PRÁTICA, NÃO FRAMEWORK. FORNECE A IMPLEMENTAÇÃO DI INVERSÃO DE

    DEPENDÊNCIA É SOBRE QUEM DEFINE UMA INTERFACE DIP RESPONSABILIDADE DE INSTANCIAR E GERENCIAR DEPENDÊNCIAS É DE UM CONTAINER OU MECANISMO EXTERNO IoC DEPENDENCY INVERSION: DEPENDER DE ABSTRAÇÕES SOLI[D]
  5. COMO TUDO SE ENCAIXA? Eu (o consumidor) decido do que

    preciso: Aqui está a interface. DI Eu (o chamador) vou te entregar o que você pediu. IoC “Quem chama quem?" O fluxo se inverte — é o framework ou o código de setup que chama a sua lógica DIP
  6. Nem todo projeto precisa de injeção de dependência. A clareza

    costuma vencer a abstração — até certo ponto. DI tem custo: mais código, mais camadas, mais conceitos. Você realmente precisa de DI?
  7. PROCURE PELOS SINAIS Código cabe em um único arquivo. Bom-senso

    é requisito!! Dependências Poucas dependências (1 ou 2). Configuração Testes Sem múltiplos ambientes/configs. Sem necessidade de testes isolados. Código
  8. { DI pode ser uma abordagem mais segura e sustentável

    à medida que a complexidade do sistema aumenta
  9. "Dependency injection is a terrible idea. It breaks Golang in

    so many ways". - disse um desenvolvedor com ranço de bibliotecas de Injeção de Dependência em Go.
  10. Constructor injection - A famosa função NewSomething(dep) - Se trata

    de passar dependências para um construtor de uma Struct - Encapsulamento - Ajuda a identificar code smells Tipos de injeção de dependência
  11. type MyService struct { repository Repository } func NewService(repository Repository)

    *MyService { return &MyService{repository: repository} }
  12. Method injection - Útil quando a dependência é diferente para

    cada request - Dependências são passadas através de funções - Usada extensivamente nas APIs da própria linguagem Tipos de injeção de dependência
  13. Property injection - Ao invés de passar as dependências via

    construtor, configura dependências depois que Struct é instanciada Tipos de injeção de dependência
  14. A arquitetura que importa é a que facilita a mudança.

    Hoje, a gente vai montar blocos, não empilhar pânico. Modularidade na prática começa com dependências bem organizadas.
  15. - NewLogger(cfg) e NewServer(logger) já são injeção de dependência -

    Separar inicialização da lógica - Inversão começa quando você deixa de instanciar para apenas "usar" A Modularização começa na mão
  16. 1. Handlers que sabem de tudo: banco, fila, cache, logger

    2. Cada construtor novo depende de outros 5 3. Testes unitários viram testes de integração disfarçados O efeito “Torre de Babel”
  17. {"Quando tudo depende de tudo, seu sistema deixa de ser

    flexível para se tornar frágil."
  18. BOAS PRÁTICAS ORQUESTRAÇÃO main.go não é lugar de lógica WIRING

    Facilita a leitura e modulariza a responsabilidade de inicialização. TESTES não devem depender da existência do main.go CRESCER Parabéns! Você tem um main.go saudável
  19. A modularidade funcionou Até o Go "puro" tem limites —

    e está tudo bem Mas está ficando pesada...
  20. O MAIN.GO FICOU ENXUTO, MAS OS ARQUIVOS DE WIRING CRESCERAM…

    AGORA TEMOS HOOKS, MÚLTIPLAS IMPLEMENTAÇÕES, LIFECYCLES… PRECISAMOS DE AJUDA PARA MANTER A ORDEM — SEM ABRIR MÃO DA CLAREZA… FERRAMENTAS NÃO RESOLVEM PROBLEMAS DE DESIGN. MAS COM UM BOM DESIGN, ELAS PODEM TE AJUDAR A MANTÊ-LO…
  21. {Geração de código Go puro em tempo de compilação, mantida

    pelo Google Totalmente transparente e fácil de depurar Ideal para projetos que já aplicam DI manualmente
  22. USAR WIRE QUANDO... EVITAR WIRE SE... Você adota construtores como

    padrão Precisa alterar dependências dinamicamente Performance e previsibilidade são prioridade Poucas dependências Você prefere erros na compilação a surpresas em tempo de execução
  23. {Wire não injeta nada por você. Ele escreve o código

    que você mesmo escreveria — só que melhor.
  24. {Fx é uma camada sobre Dig: adiciona lifecycle hooks, logs,

    módulos "Battle tested: Fx is the backbone of nearly all Go services at Uber" - retirado da documentação do Fx.
  25. Usar Fx/Dig quando... Evitar Fx/Dig se... Você tem muitos módulos

    dinâmicos Quer rastrear cada dependência de forma clara Almeja controle fino do ciclo de vida Prefere evitar reflexão e runtime injection Quer produtividade rápida para MVP ou microsserviços Seu time exige rastreabilidade total
  26. CRITÉRIO MANUAL WIRE DIG FX 🔧 Complexidade do sistema Baixa

    Média a alta Alta Muito alta (micro serviços, múltiplos domínios) 📦 Controle sobre dependências Total Total (gerado em build) Parcial (via container) Parcial com conveniência 🚀 Produtividade no bootstrap Baixa (boilerplate) Média Alta (pouco código) Muito alta (hooks, auto start, logs) 🧪 Testabilidade & Simulação Excelente Excelente Boa Média (por conta da abstração reflexiva) 🔍 Rastreabilidade & depuração Total transparência Total transparência Parcial (reflexão) Baixa (opaca por padrão) 🧰 Requer conhecimento prévio Nenhum além de Go idiomático Médio (estrutura declarativa + wire CLI) Médio (inversão via dig.Container) Alto (ciclo de vida, binding, logs automáticos)
  27. INJEÇÃO DE DEPENDÊNCIA NÃO SE TRATA DE TECNOLOGIA. TRATA-SE DE

    COMO VOCÊ ESTRUTURA SEU SOFTWARE… NENHUMA FERRAMENTA CORRIGE UM PROBLEMA DE DESIGN. MAS, COM UM BOM DESIGN, A FERRAMENTA CERTA ECONOMIZA TEMPO — E DOR DE CABEÇA… VOCÊ NÃO COMEÇA COM INJEÇÃO DE DEPENDÊNCIA. VOCÊ CHEGA ATÉ ELA… USE TÉCNICAS DE INJEÇÃO DE DEPENDÊNCIA QUE ESCALEM COM SEU TIME E SUA BASE DE CÓDIGO — NÃO APENAS COM SUAS PREFERÊNCIAS…
  28. {Injeção de dependência não é só sobre como as coisas

    se conectam. É sobre tornar mudanças futuras mais seguras, rápidas e menos dolorosas.
  29. 1. Tudo começa com a criação de um container container

    := dig.New() 2. Depois, vem as declarações das dependências container.Provide(NewService, dig.As(new(MyService))) 3. Por último, invoque! container.Invoke(func(s *http.Server)) Dig - Anexo 1
  30. - DI similar ao Dig, mas com objetos mais poderosos

    fx.Module("inventory", fx.Provide( fx.Annotate(NewService, fx.As(new(InventoryService))), ), ) - Plugue: fx.New(inventory.Module...) - O objeto fx.Lifecycle Fx - Anexo 2