A pergunta "como o usuário chega até o meu pod?" tem uma resposta com quatro camadas, e a confusão entre elas é responsável por boa parte do tempo perdido em cluster novo. Service, Ingress, Ingress Controller e load balancer não são alternativas entre si — são peças diferentes de um mesmo caminho.
Entender qual peça faz o quê resolve de uma vez os sintomas clássicos: o LoadBalancer que fica eternamente pendente, o Ingress criado que não responde nada, o certificado que não é apresentado e o endereço de origem que chega errado na aplicação.
As camadas, de dentro para fora
Pod tem endereço, mas ele é efêmero. Morreu, nasce outro com outro endereço. Não se aponta nada para pod.
Service dá um nome e um endereço estáveis para um conjunto de pods, e distribui as conexões entre eles. Ele é o alicerce de tudo. Existe em tipos:
ClusterIP— acessível só dentro do cluster. É o padrão e o correto para comunicação entre serviços.NodePort— abre a mesma porta alta em todos os nós. Serve para laboratório e para casos específicos; não é como se expõe aplicação para usuário.LoadBalancer— pede ao ambiente um balanceador externo com endereço próprio.
Ingress é uma regra de roteamento HTTP: "requisições para loja.exemplo.com no caminho /api vão para o service X". É apenas a declaração — ela não faz nada sozinha.
Ingress Controller é o que lê essas regras e efetivamente roteia o tráfego. É um pod rodando um proxy reverso (NGINX, Traefik, HAProxy, Envoy) que se configura sozinho a partir dos objetos Ingress.
Load balancer é o que traz o tráfego de fora para dentro do cluster e entrega ao controller.
O caminho completo: usuário → load balancer → Ingress Controller → Service → Pod.
Os dois erros mais comuns, explicados
"Criei o Ingress e nada acontece"
Porque não há Ingress Controller instalado. O objeto Ingress é uma regra escrita num quadro que ninguém está lendo.
Cluster gerenciado de provedor de nuvem geralmente já traz um. Cluster instalado por você, não. Instalar o controller é um passo próprio, e o Ingress precisa referenciar qual controller deve atendê-lo — em cluster com mais de um, essa referência é obrigatória.
"Meu Service LoadBalancer fica pendente para sempre"
Porque o tipo LoadBalancer pede ao ambiente que provisione um balanceador. Na nuvem, o provedor atende. Em cluster próprio, em Proxmox, em bare metal, não há ninguém para atender — e o objeto fica pendente indefinidamente.
A solução em ambiente próprio é instalar algo que cumpra esse papel. As opções práticas:
- MetalLB, que reserva uma faixa de endereços da sua rede e os atribui aos services, anunciando-os por ARP ou por BGP. É a opção mais usada e funciona bem.
- Balanceador externo — HAProxy, ou um appliance que você já tem — apontando para os nós, com o controller exposto por NodePort atrás dele.
- Roteamento por BGP do próprio ambiente, quando a rede permite.
Essa é uma das primeiras coisas a resolver ao montar Kubernetes fora de nuvem, e uma das que mais surpreende quem só operou cluster gerenciado.
Ingress: o que ele faz bem e onde trava
O Ingress cobre o caso comum com competência:
- Roteamento por domínio e por caminho.
- Terminação de TLS, com os certificados guardados como segredos.
- Integração com emissão automática de certificado.
E trava em três pontos, que explicam por que a Gateway API existe:
- A especificação cobre pouco. Reescrita de caminho, tempo limite, tamanho de corpo, autenticação, divisão de tráfego por peso — nada disso está no padrão. Cada controller resolve com anotações próprias, o que significa que o seu Ingress cheio de anotações não é portável: trocar de controller é reescrever tudo.
- Não há separação de responsabilidades. O mesmo objeto mistura o que é da infraestrutura (certificado, endereço, política de rede) e o que é da aplicação (caminhos e destinos). Em cluster compartilhado entre times, isso vira problema de permissão e de colisão.
- É só HTTP. Para TCP e UDP, cada controller inventa o próprio mecanismo.
Gateway API: o sucessor
A Gateway API é o padrão mais recente para entrada de tráfego, e o desenho dela responde diretamente às limitações acima. Ela divide o que era um objeto em três papéis:
| Recurso | Quem cuida | O que define |
|---|---|---|
GatewayClass | Fornecedor da infraestrutura | Qual implementação atende |
Gateway | Time de plataforma | Endereço, portas, certificados, quem pode usar |
HTTPRoute (e TCPRoute, GRPCRoute) | Time de aplicação | Regras de roteamento do seu serviço |
O ganho concreto: o time de plataforma cria o Gateway e define quais namespaces podem anexar rotas a ele. Os times de aplicação criam suas rotas sem tocar em certificado nem em endereço. A permissão fica natural, em vez de ser recriada com ferramentas externas.
Além disso, recursos que antes eram anotação viram campos padronizados: divisão de tráfego por peso — que habilita canary nativo —, roteamento por cabeçalho, reescrita, espelhamento de tráfego e suporte a protocolos além de HTTP.
Devo migrar agora? A recomendação honesta:
- Cluster novo: comece pela Gateway API, se o controller escolhido a suporta bem. Você evita a migração futura.
- Cluster existente com Ingress funcionando: não há urgência. Ingress continua suportado e não vai sumir tão cedo. Migre quando precisar de algo que ele não entrega — divisão de tráfego por peso, roteamento por cabeçalho, separação de permissão entre times.
- Coexistência é possível e é o caminho mais tranquilo: os dois rodam no mesmo cluster durante a transição.
Escolher o controller
| Controller | Perfil | Bom quando |
|---|---|---|
| NGINX | O mais difundido | Você quer o caminho mais documentado e com mais respostas prontas |
| Traefik | Descoberta automática, painel próprio | Time pequeno, quer simplicidade e bom suporte a Gateway API |
| HAProxy | Desempenho e controle fino | Alto volume, necessidade de ajuste detalhado |
| Envoy (via Contour, Istio, Gateway) | Base de service mesh | Já usa mesh, ou quer Gateway API madura |
O critério mais prático: o que o time já sabe operar, e o que tem boa implementação do padrão que você escolheu. Todos entregam o básico bem.
Os detalhes que quebram em produção
Endereço de origem perdido. A aplicação vê o endereço do proxy, não do usuário. Isso quebra log, bloqueio por IP e limitação por origem. A correção envolve o cabeçalho de encaminhamento e, em service LoadBalancer, a política de tráfego externo local — que preserva a origem, ao custo de a distribuição ficar menos uniforme entre os nós.
Conexão persistente e WebSocket. Precisam de tempo limite maior e de configuração explícita em alguns controllers. Sintoma típico: conexão caindo a cada 60 segundos.
Tamanho de corpo. Upload falhando com erro de payload grande é limite padrão do controller, não da aplicação.
Certificado não apresentado. Quase sempre o segredo do certificado está em namespace diferente do Ingress. O Ingress só enxerga segredos do próprio namespace — e esse é o item que mais consome tempo de quem está começando.
Encerramento sem drenagem. Ao atualizar o controller, conexões em andamento são cortadas. Encerramento gracioso e mais de uma réplica resolvem.
Réplica única do controller. É ponto único de falha para todo o tráfego de entrada do cluster. Mínimo de duas réplicas, em nós diferentes.
O desenho que funciona
Para um cluster em infraestrutura própria:
- MetalLB com uma faixa de endereços reservada na sua rede.
- Ingress Controller ou Gateway com no mínimo duas réplicas, em nós distintos, exposto por um service
LoadBalancer. - Emissão automática de certificado integrada, com validação por DNS.
- Política de tráfego externo local quando o endereço de origem importa.
- DNS apontando os domínios para o endereço do balanceador.
- Métricas do controller no painel: taxa de erro por rota, latência, conexões ativas.
- Limite de requisições e proteção básica no controller, antes de chegar à aplicação.
O item 6 é subestimado: o controller é o melhor lugar do cluster para medir experiência real do usuário, porque vê todo o tráfego de entrada antes de qualquer aplicação.
Erros comuns
- Criar Ingress sem instalar Ingress Controller.
- Esperar que
LoadBalancerfuncione em cluster próprio sem MetalLB ou equivalente. - Expor aplicação com NodePort em produção.
- Segredo do certificado em namespace diferente do Ingress.
- Controller com réplica única, virando ponto único de falha.
- Encher o Ingress de anotações específicas e ficar preso ao controller.
- Perder o endereço de origem e quebrar log e bloqueio por IP.
- Tempo limite padrão derrubando WebSocket e conexões longas.
- Limite de corpo padrão quebrando upload.
- Migrar para Gateway API sem necessidade, só por ser mais novo.
- Não monitorar o controller, perdendo a melhor fonte de métrica de usuário.
Onde a Solvefy/Cloud entra
Montamos a entrada de tráfego de clusters em infraestrutura própria — incluindo Kubernetes sobre Proxmox, que é um desenho frequente entre nossos clientes: MetalLB com faixa reservada, controller redundante, certificados automáticos com validação por DNS, preservação de endereço de origem, limites e tempos limite ajustados à aplicação e métricas de entrada no painel. Também conduzimos a migração de Ingress para Gateway API quando há motivo concreto — e dizemos quando não há.
Seu tráfego entra no cluster do jeito certo? Diagnóstico gratuito, sem compromisso, em solvefy.cloud.
Solvefy/Cloud — Infraestrutura que cresce com você.