Namespaces: isolamento dentro do cluster

1. O que são Namespaces no Kubernetes?

Namespaces no Kubernetes são mecanismos de isolamento lógico que permitem particionar um cluster físico em múltiplos ambientes virtuais. Diferentemente dos namespaces do Linux, que isolam processos e recursos do sistema operacional, os namespaces do Kubernetes isolam objetos e recursos da API do Kubernetes.

Enquanto namespaces Linux operam no nível do kernel — isolando PID, rede, montagem, IPC, UTS, usuário e cgroups —, namespaces Kubernetes são abstrações de alto nível que organizam objetos como Pods, Services, Deployments e ConfigMaps dentro de um cluster.

Casos de uso comuns incluem:
- Ambientes: criar namespaces separados para desenvolvimento (dev), homologação (staging) e produção (prod) dentro do mesmo cluster
- Multi-tenancy: isolar equipes ou projetos diferentes (ex: time-pagamentos, time-catalogo)
- Controle de acesso: aplicar políticas RBAC específicas por namespace
- Gerenciamento de recursos: limitar CPU e memória por namespace

Por padrão, o Kubernetes cria quatro namespaces iniciais: default (onde os objetos vão se nenhum namespace for especificado), kube-system (componentes do sistema), kube-public (recursos acessíveis a todos) e kube-node-lease (leases de heartbeats dos nós).

2. Trabalhando com Namespaces: Comandos Essenciais

Criando namespaces

Via comando direto:

kubectl create namespace dev

Via arquivo YAML (namespace-dev.yaml):

apiVersion: v1
kind: Namespace
metadata:
  name: dev
  labels:
    environment: development
    team: plataforma

Aplicando:

kubectl apply -f namespace-dev.yaml

Listando e visualizando

# Listar todos os namespaces
kubectl get namespaces

# Ver detalhes de um namespace específico
kubectl describe namespace dev

# Listar pods de um namespace específico
kubectl get pods -n dev

Alternando entre namespaces

Para evitar digitar -n <namespace> toda vez, configure o contexto:

# Definir namespace padrão no contexto atual
kubectl config set-context --current --namespace=dev

# Verificar configuração atual
kubectl config view --minify | grep namespace

3. Escopo de Recursos dentro de Namespaces

Nem todos os recursos do Kubernetes são namespaced. É crucial entender essa distinção:

Recursos namespaced (existem dentro de um namespace específico)

  • Pods, Services, Deployments, StatefulSets, ConfigMaps, Secrets
  • Ingress, NetworkPolicies, ResourceQuotas, LimitRanges

Recursos cluster-scoped (não pertencem a nenhum namespace)

  • Nodes, PersistentVolumes, Namespaces, ClusterRoles, ClusterRoleBindings
  • StorageClasses, CustomResourceDefinitions (CRDs)

Para verificar se um recurso é namespaced:

kubectl api-resources --namespaced=true
kubectl api-resources --namespaced=false

DNS interno por namespace

O Kubernetes possui um sistema de DNS interno. Um serviço chamado meu-servico no namespace dev é acessível como:

meu-servico.dev.svc.cluster.local

Isso permite descoberta de serviços entre namespaces. Para acessar um serviço de outro namespace, use o FQDN:

curl http://servico-pagamentos.prod.svc.cluster.local:8080

4. Gerenciando Acesso com ResourceQuotas e LimitRanges

ResourceQuota: limitando recursos por namespace

Arquivo quota-dev.yaml:

apiVersion: v1
kind: ResourceQuota
metadata:
  name: quota-dev
  namespace: dev
spec:
  hard:
    requests.cpu: "4"
    requests.memory: "8Gi"
    limits.cpu: "8"
    limits.memory: "16Gi"
    persistentvolumeclaims: "5"
    pods: "20"
    services: "10"

LimitRange: definindo limites padrão para Pods/Containers

Arquivo limits-dev.yaml:

apiVersion: v1
kind: LimitRange
metadata:
  name: limits-dev
  namespace: dev
spec:
  limits:
  - max:
      cpu: "2"
      memory: "4Gi"
    min:
      cpu: "100m"
      memory: "128Mi"
    default:
      cpu: "500m"
      memory: "512Mi"
    defaultRequest:
      cpu: "200m"
      memory: "256Mi"
    type: Container

Aplicando ambos:

kubectl apply -f quota-dev.yaml
kubectl apply -f limits-dev.yaml

Quando um ResourceQuota é aplicado, todos os Pods devem especificar requests e limits. O LimitRange garante que, se não forem especificados, valores padrão serão aplicados.

5. Políticas de Rede e Isolamento entre Namespaces

Por padrão, todos os Pods em um cluster Kubernetes podem se comunicar entre si. NetworkPolicies mudam esse comportamento.

Isolamento padrão: negar todo tráfego

Arquivo default-deny.yaml:

apiVersion: networking.k8s.io/v1
kind: NetworkPolicy
metadata:
  name: default-deny
  namespace: dev
spec:
  podSelector: {}
  policyTypes:
  - Ingress
  - Egress

Permitindo tráfego apenas de um namespace específico

Arquivo allow-from-prod.yaml:

apiVersion: networking.k8s.io/v1
kind: NetworkPolicy
metadata:
  name: allow-from-prod
  namespace: dev
spec:
  podSelector: {}
  policyTypes:
  - Ingress
  ingress:
  - from:
    - namespaceSelector:
        matchLabels:
          environment: production
    ports:
    - protocol: TCP
      port: 80

Essa política permite tráfego HTTP (porta 80) apenas de Pods no namespace com label environment: production. Todos os outros tráfegos são bloqueados.

6. Boas Práticas e Padrões de Organização

Estruturação de namespaces

Critério Exemplo Vantagem
Por ambiente dev, staging, prod Isolamento claro, políticas diferentes
Por equipe time-pagamentos, time-catalogo Autonomia, RBAC granular
Por aplicação app-web, app-api, app-worker Escopo limitado, fácil troubleshooting
Híbrido dev-pagamentos, prod-catalogo Combina benefícios

Uso de labels e annotations

apiVersion: v1
kind: Namespace
metadata:
  name: time-pagamentos
  labels:
    environment: production
    team: pagamentos
    cost-center: fin-123
  annotations:
    owner: "joao.silva@empresa.com"
    sla: "99.9%"
    created-by: "terraform"

Migração entre namespaces

Para mover recursos entre namespaces:
1. Exporte a configuração: kubectl get deployment meu-app -n dev -o yaml > deploy.yaml
2. Remova campos gerados automaticamente (uid, resourceVersion, etc.)
3. Altere o campo namespace no YAML
4. Aplique no novo namespace: kubectl apply -f deploy.yaml -n prod
5. Delete do namespace antigo: kubectl delete deployment meu-app -n dev

7. Monitoramento e Troubleshooting em Namespaces

Visualizando logs filtrados

# Logs de todos os pods em um namespace
kubectl logs -n dev --all-containers=true --prefix=true

# Seguir logs em tempo real
kubectl logs -n dev -l app=meu-servico --tail=50 -f

Métricas por namespace

# Top pods por namespace (requer metrics-server)
kubectl top pods -n dev

# Top pods ordenados por uso de CPU
kubectl top pods -n dev --sort-by=cpu

# Verificar uso de recursos da quota
kubectl describe resourcequota quota-dev -n dev

Problemas comuns e soluções

Conflito de nomes: dois serviços com mesmo nome em namespaces diferentes funcionam, mas cuidado com DNS.

Quota excedida: ao criar um Pod, erro exceeded quota. Verifique:

kubectl describe quota -n dev
kubectl get events -n dev --sort-by='.lastTimestamp'

NetworkPolicy bloqueando tráfego: teste conectividade com:

kubectl run test-pod --image=busybox -n dev --rm -it -- sh
wget -O- http://servico.prod.svc.cluster.local:80

Ferramentas úteis:
- kubectl ns (plugin kubectx) para alternar rapidamente entre namespaces
- k9s para visualização em terminal com filtro por namespace
- stern para logs multiplexados de múltiplos pods em um namespace
- Dashboards customizados no Grafana com filtro namespace

Referências