Pular para o conteúdo

Service que não responde

Intermediário14 min de leiturakubernetes

“O serviço não responde” pode quebrar em seis lugares diferentes entre o cliente e o processo. Este roteiro percorre cada salto na ordem, e cada passo elimina uma classe de causa — não pule etapas, porque o erro quase sempre está antes de onde você suspeita.

Comece com um Pod de diagnóstico dentro do mesmo namespace:

Janela do terminal
kubectl run diag --rm -it --image=nicolaka/netshoot -n <ns> -- bash
Janela do terminal
nslookup pedidos # dentro do namespace
nslookup pedidos.loja.svc.cluster.local

Se não resolve:

  • Confira se o Service existe: kubectl get svc pedidos -n <ns>.
  • Confira o namespace — de outro namespace, o nome curto não resolve; use o FQDN.
  • Teste o DNS do cluster: kubectl -n kube-system get pods -l k8s-app=kube-dns e os logs do CoreDNS. Resolução lenta e intermitente costuma ser CoreDNS sem réplicas suficientes ou ndots gerando consultas demais.

Se resolve, você tem um ClusterIP. Siga.

Este é o passo que resolve a maioria dos casos.

Janela do terminal
kubectl get endpointslice -n <ns> -l kubernetes.io/service-name=pedidos
kubectl describe svc pedidos -n <ns> | grep -i endpoints

Lista vazia significa que nenhum Pod pronto casa com o selector. Duas causas possíveis, e o próximo passo separa uma da outra: selector errado, ou Pods não prontos.

Janela do terminal
kubectl get svc pedidos -n <ns> -o jsonpath='{.spec.selector}'; echo
kubectl get pods -n <ns> --show-labels | head
# teste o selector diretamente:
kubectl get pods -n <ns> -l app=pedidos

Se o comando com o selector não devolve Pod nenhum, o problema é divergência de label — app: pedidos contra app.kubernetes.io/name: pedidos é o clássico. Corrija o Service ou o template do Pod (mudar o selector de um Deployment existente exige recriá-lo).

Pod não pronto não entra no endpoint, mesmo com o label certo.

Janela do terminal
kubectl get pods -n <ns> -l app=pedidos # coluna READY: 0/1 é o sintoma
kubectl describe pod <pod> -n <ns> | sed -n '/Events/,$p'

Readiness reprovando aparece nos eventos como Readiness probe failed. Confira caminho, porta e tempo: probe apontando para porta errada, ou com initialDelaySeconds menor que o tempo de boot, mantém o Pod fora do rodízio para sempre.

Elimine a rede do problema falando direto com o Pod:

Janela do terminal
kubectl port-forward pod/<pod> 8080:8080 -n <ns> # em outro terminal: curl localhost:8080
# ou, de dentro do Pod de diagnóstico:
curl -sv http://<IP-DO-POD>:8080/healthz

E confira o mapeamento de portas do Service, que é onde a confusão mora:

Janela do terminal
kubectl get svc pedidos -n <ns> -o yaml | grep -A5 ports
# port: a porta do Service (o que o cliente chama)
# targetPort: a porta do container (onde a aplicação escuta) — é aqui que se erra

Outro item frequente: a aplicação escutando em 127.0.0.1 em vez de 0.0.0.0. Nesse caso ela responde dentro do container e não responde de fora.

Janela do terminal
kubectl get networkpolicy -n <ns>
kubectl describe networkpolicy -n <ns>

Lembre que basta uma política selecionar o Pod para que tudo que não estiver explicitamente permitido seja negado. Erros comuns: esquecer o tráfego de DNS para o kube-system, ou liberar o namespace de origem sem liberar a porta.

Teste rápido de hipótese: conecte-se de um Pod no mesmo namespace e de outro namespace. Se o primeiro funciona e o segundo não, é política.

Se o acesso interno funciona e o externo não, o problema está na borda:

Janela do terminal
kubectl describe ingress pedidos -n <ns> # backend correto? TLS emitido?
kubectl get svc -n ingress-nginx # o LoadBalancer recebeu IP externo?
kubectl logs -n ingress-nginx -l app.kubernetes.io/name=ingress-nginx --tail=50

Verifique também ingressClassName, o registro DNS apontando para o endereço certo e, em type: LoadBalancer pendente, se o cloud controller conseguiu provisionar (eventos do Service explicam).

Sintoma Onde olhar
Nome não resolve CoreDNS, namespace, FQDN
Endpoints vazios Selector vs labels, readiness
Conexão recusada targetPort, endereço de escuta da aplicação
Timeout NetworkPolicy, security group, rota
Funciona por dentro, não por fora Ingress, DNS, LoadBalancer, TLS
Intermitente Réplicas não prontas, drenagem no deploy, DNS lento
  • Nome resolve de dentro do cluster.
  • EndpointSlice lista os IPs esperados.
  • Todos os Pods READY.
  • port e targetPort conferidos contra a porta real da aplicação.
  • NetworkPolicy revisada, incluindo DNS.
  • Acesso externo verificado no Ingress e no DNS.