0 XP
Módulo 8 · Kubernetes e Helm

Deployment, Service, ConfigMap e Secret

Intermediário 50 min+25 XPkubectlYAML

Objetivos desta aula

  • Escrever manifests corretos
  • Injetar configuração e segredo
  • Expor a aplicação internamente

Deployment gerencia ReplicaSets, que gerenciam pods, e é o que permite rollout gradual e rollback. Service dá um nome estável e balanceamento para um conjunto de pods selecionado por labels: ClusterIP para uso interno, NodePort para acesso direto em laboratório, LoadBalancer para provisionar balanceador na nuvem.

Configuração vem de ConfigMap; dado sensível, de Secret. Importante: Secret padrão é apenas base64, não criptografia — o que protege é RBAC, criptografia em repouso no etcd e não versionar o valor. Para GitOps, use Sealed Secrets, SOPS ou External Secrets Operator.

Labels e selectors são a cola de tudo. Selector do Service que não casa com as labels do pod produz o clássico 'Service sem endpoints', em que a aplicação está de pé mas nada chega nela.

1. Pod: a menor unidade

Um Pod é um ou mais contêineres que compartilham rede (mesmo IP) e volumes. Pods são descartáveis: nunca crie Pods soltos em produção, crie um controller que os recria.

2. Deployment e ReplicaSet

O Deployment gerencia ReplicaSets, que gerenciam Pods. Ao trocar a imagem, o Deployment cria um novo ReplicaSet e faz rolling update: sobe Pods novos e derruba antigos aos poucos, controlado por maxSurge e maxUnavailable.

3. Labels e selectors: a cola de tudo

Deployment encontra seus Pods por labels; Service encontra para onde mandar tráfego por labels. Se o selector não bate com as labels do template, nada funciona — é a primeira coisa a conferir.

4. Service: endereço estável

  • ClusterIP: IP interno e nome DNS (api.cloudshop.svc.cluster.local)
  • NodePort: porta em todos os nós (uso raro)
  • LoadBalancer: pede um balanceador à nuvem

O Service mantém uma lista de endpoints com os IPs dos Pods prontos.

5. ConfigMap e Secret

Configuração fica fora da imagem: ConfigMap para dados comuns, Secret para sensíveis. Atenção: Secret é só base64, não criptografia — habilite criptografia do etcd e restrinja com RBAC. Injete como variáveis (envFrom) ou arquivos (volume).

6. Rollout na prática

kubectl rollout status acompanha, rollout history mostra versões e rollout undo volta. Mudar só um ConfigMap não reinicia Pods; use um hash da config como anotação (Helm faz isso fácil).

Na prática

Manifests da API do CloudShop

yaml

apiVersion: v1
kind: ConfigMap
metadata: { name: cloudshop-api-config }
data:
  NODE_ENV: production
  DATABASE_HOST: cloudshop-db
  DATABASE_PORT: "5432"
---
apiVersion: apps/v1
kind: Deployment
metadata:
  name: cloudshop-api
  labels: { app: cloudshop, component: api }
spec:
  replicas: 2
  revisionHistoryLimit: 5
  strategy:
    type: RollingUpdate
    rollingUpdate: { maxSurge: 1, maxUnavailable: 0 }
  selector:
    matchLabels: { app: cloudshop, component: api }
  template:
    metadata:
      labels: { app: cloudshop, component: api }
    spec:
      securityContext:
        runAsNonRoot: true
        runAsUser: 10001
      containers:
        - name: api
          image: ghcr.io/sua-org/cloudshop/api:v1.2.0
          ports: [{ containerPort: 3000, name: http }]
          envFrom:
            - configMapRef: { name: cloudshop-api-config }
          env:
            - name: DATABASE_PASSWORD
              valueFrom:
                secretKeyRef: { name: cloudshop-db, key: password }
          resources:
            requests: { cpu: 100m, memory: 128Mi }
            limits:   { cpu: 500m, memory: 256Mi }
          securityContext:
            allowPrivilegeEscalation: false
            readOnlyRootFilesystem: true
            capabilities: { drop: ["ALL"] }
---
apiVersion: v1
kind: Service
metadata: { name: cloudshop-api }
spec:
  type: ClusterIP
  selector: { app: cloudshop, component: api }
  ports: [{ port: 80, targetPort: http }]

Nota de segurança: Nunca versione Secret com valor em base64 no Git. Use External Secrets ou SOPS com chave gerenciada.

Aplicar e depurar

bash

kubectl apply -f k8s/
kubectl get deploy,rs,pod,svc
kubectl describe deploy cloudshop-api | tail -20
kubectl get endpoints cloudshop-api      # vazio = selector nao casa
kubectl logs deploy/cloudshop-api --tail=50
kubectl port-forward svc/cloudshop-api 8080:80
kubectl run tmp --rm -it --image=curlimages/curl -- sh -c 'curl -s cloudshop-api/health'

API do CloudShop: Deployment + Service + ConfigMap

yaml

apiVersion: v1
kind: ConfigMap
metadata: { name: api-config, namespace: cloudshop }
data:
  LOG_LEVEL: info
  DB_HOST: postgres.cloudshop.svc.cluster.local
---
apiVersion: apps/v1
kind: Deployment
metadata: { name: api, namespace: cloudshop }
spec:
  replicas: 3
  strategy:
    rollingUpdate: { maxSurge: 1, maxUnavailable: 0 }   # nunca fica abaixo de 3
  selector: { matchLabels: { app: api } }
  template:
    metadata: { labels: { app: api } }                  # precisa bater com o selector
    spec:
      containers:
        - name: api
          image: ghcr.io/cloudshop/api:1.4.2              # tag fixa, nunca latest
          ports: [{ containerPort: 3000 }]
          envFrom:
            - configMapRef: { name: api-config }
            - secretRef: { name: api-db }                 # senha do banco
---
apiVersion: v1
kind: Service
metadata: { name: api, namespace: cloudshop }
spec:
  selector: { app: api }
  ports: [{ port: 80, targetPort: 3000 }]

Atualizar e voltar versão

bash

kubectl -n cloudshop set image deploy/api api=ghcr.io/cloudshop/api:1.5.0
kubectl -n cloudshop rollout status deploy/api
kubectl -n cloudshop get endpoints api      # IPs dos Pods prontos
kubectl -n cloudshop rollout undo deploy/api   # volta para a versão anterior

Por que isso importa

Estes quatro objetos cobrem 80% do trabalho diário com Kubernetes.

Erro comum

Selector do Service divergente das labels do pod, gerando Service sem endpoints.

Dica de produção

maxUnavailable: 0 garante deploy sem janela de indisponibilidade quando há réplicas suficientes.

Alerta de segurança

runAsNonRoot, readOnlyRootFilesystem e drop de capabilities devem ser o padrão, não a exceção.

Pergunta de entrevista

Service existe, pods rodando, mas nada responde. O que você verifica?

Glossário

selector
Regra de labels que define quais pods pertencem a um Service ou controller.
envFrom
Forma de injetar todas as chaves de um ConfigMap como variáveis de ambiente.
ReplicaSet
Garante um número fixo de Pods iguais; é gerenciado pelo Deployment.
Rolling update
Troca gradual de Pods antigos por novos sem indisponibilidade.
Endpoints
Lista de IPs de Pods prontos para os quais o Service envia tráfego.

Conexão com o CloudShop

Traduzir os serviços do Compose em Deployments e Services do CloudShop.

Quiz da aula

  1. 1. Service sem endpoints normalmente indica:

  2. 2. O Service não entrega tráfego e 'kubectl get endpoints' está vazio. Causa mais provável?

  3. 3. Um Secret do Kubernetes, por padrão, é:

Minhas anotações

Salvo automaticamente neste navegador.

AnteriorPróxima