
Curso Kubernetes 06 — CNI: flannel, Cilium e NetworkPolicy
Todo pod precisa de um IP e de falar com outros pods. Quem entrega isso é a CNI (Container Network Interface). Mas há uma pegadinha que derruba muita gente: nem toda CNI aplica NetworkPolicy.
Já vi um cluster com políticas de rede criadas, revisadas e “aprovadas” — e nenhum efeito. O flannel estava cuidando da rede; a política era só um objeto decorativo no etcd.
Selo do curso: testado em Kubernetes 1.35 e Ubuntu 24.04.
O que a CNI faz
- Atribui IP ao pod.
- Configura rotas entre nós.
- Cuida do encaminhamento entre pods e Services (em conjunto com o kube-proxy).
- Em algumas implementações, aplica políticas de rede.
Modelos comuns:
| Modelo | Como funciona | Exemplos |
|---|---|---|
| Overlay (VXLAN) | encapsula pacotes entre nós | flannel, Canal |
| Roteado | rotas/BGP entre nós | Calico (BGP), Cilium (native routing) |
| eBPF | datapath no kernel | Cilium |
flannel: simples e honesto
O flannel é ótimo para laboratório: instala fácil, funciona e tem pouca manutenção. Ele cria uma rede VXLAN e distribui um /24 por nó.
kubectl apply -f https://github.com/flannel-io/flannel/releases/latest/download/kube-flannel.yml
kubectl -n kube-flannel get pods -o wide
Limitação importante: flannel não implementa NetworkPolicy. O objeto é aceito pela API e armazenado, mas não há agente aplicando a regra. Se você precisa segmentar, precisa de Cilium, Calico ou outro policy engine.
Cilium e Calico: política de verdade
- Cilium usa eBPF, tem observabilidade de fluxo (Hubble), políticas L3/L4/L7 e pode substituir o kube-proxy.
- Calico é maduro, baseado em iptables/eBPF, com política e BGP.
Neste curso não vamos trocar a CNI agora — trocar CNI em cluster vivo exige janela. Mas vamos entender o suficiente para não cair no conto do flannel.
NetworkPolicy em 5 minutos
Uma política seleciona pods por label e define quem pode entrar/sair.
Default-deny de ingress no namespace:
apiVersion: networking.k8s.io/v1
kind: NetworkPolicy
metadata:
name: default-deny-ingress
namespace: demo
spec:
podSelector: {}
policyTypes:
- Ingress
Permitir apenas do pod client:
apiVersion: networking.k8s.io/v1
kind: NetworkPolicy
metadata:
name: allow-client
namespace: demo
spec:
podSelector:
matchLabels:
app: server
policyTypes:
- Ingress
ingress:
- from:
- podSelector:
matchLabels:
app: client
ports:
- protocol: TCP
port: 80
Permitir do ingress-nginx:
ingress:
- from:
- namespaceSelector:
matchLabels:
kubernetes.io/metadata.name: ingress-nginx
Permitir probes do kubelet (que vêm do IP do nó):
ingress:
- from:
- ipBlock:
cidr: 192.168.56.0/24
Laboratório: provar (ou não) a política
Crie o namespace e dois pods:
kubectl create ns demo
kubectl -n demo run server --image=nginx:1.27 --port=80 --labels=app=server
kubectl -n demo run client --image=curlimages/curl:8.10.1 --labels=app=client --command -- sleep 3600
Teste antes da política:
kubectl -n demo exec client -- curl -s -o /dev/null -w '%{http_code}\n' http://server
# 200
Aplique o default-deny e o allow-client:
kubectl apply -f default-deny.yaml
kubectl apply -f allow-client.yaml
Teste de novo:
kubectl -n demo exec client -- curl -s -o /dev/null -w '%{http_code}\n' http://server
- Em Cilium/Calico: o cliente autorizado continua 200; um pod sem o label
clientrecebe timeout. - Em flannel: provavelmente continua 200 para todo mundo — a política não é aplicada.
Esse teste é o mais importante do capítulo. Se ele não bloquear, sua segmentação é ficção.
Trocar a CNI sem derrubar tudo
Se você decidiu migrar para Cilium:
- Planeje janela de manutenção.
- Faça backup (etcd/Velero).
- Instale Cilium com
kubeProxyReplacement=false(mantém o kube-proxy) e IPAM compatível com opodCIDR. - Valide
cilium statusem todos os nós. - Remova o flannel nó a nó, com drain/cordon, garantindo pods saudáveis.
- Aplique as NetworkPolicies e rode o teste negativo.
- Tenha rollback: reinstalar flannel e restaurar o CNI config.
Não faça isso em produção sem ensaio. Em laboratório, quebre à vontade.
Erros comuns
| Sintoma | Causa provável |
|---|---|
Pods Pending ou NotReady |
CNI não instalada ou DaemonSet com erro |
| DNS quebrado | CoreDNS sem rede ou política bloqueando 53 |
| Política “não faz nada” | CNI sem suporte a NetworkPolicy |
| Probes falhando após política | kubelet bloqueado; permita o IP do nó |
| Tráfego entre namespaces bloqueado | falta de namespaceSelector explícito |
| IP exhaustion | CIDR pequeno para o número de pods |
Checklist
- [ ] Sei qual CNI está no cluster.
- [ ] Sei se ela aplica NetworkPolicy.
- [ ] Testei default-deny com um pod não autorizado.
- [ ] Liberei DNS e probes.
- [ ] Tenho plano de rollback se trocar a CNI.
- [ ] Documentei as políticas no repositório.
Glossário
- CNI: interface que configura a rede dos pods.
- overlay: rede encapsulada sobre a rede física.
- NetworkPolicy: regra de ingress/egress por seletor.
- default-deny: nega tudo que não for explicitamente permitido.
- eBPF: execução de programas no kernel, usada pelo Cilium.
Próximo
Agora que a rede está sob controle, vamos organizar o cluster: namespaces, labels, quotas, PDB e o que realmente protege uma carga durante uma manutenção.
Próximo: Curso Kubernetes 07 — Namespaces, labels, quotas e PDB
Continuar a ler
Leia também
KubernetesKubernetes de Verdade — do zero ao cluster em produção
Uma trilha prática para entender, montar e operar um cluster Kubernetes — do primeiro pod ao failover do Postgres.
4 min de leitura
KubernetesCurso Kubernetes 28 — DR e capstone: provar que o cluster volta
RPO, RTO e drills reais: cenários de desastre, runbook, restore medido e o capstone que fecha o curso com um cluster que se recupera.
5 min de leitura
KubernetesCurso Kubernetes 27 — SLO/SLI, on-call e postmortem blameless
O que prometer, como medir e o que fazer quando o erro estoura: SLI, SLO, error budget, alertas que acordam alguém e postmortem sem caça às bruxas.
4 min de leitura
Comentários
Ainda sem comentários
Seja o primeiro a compartilhar sua opinião sobre este artigo.
Deixe um comentário