Avançado DevSecOps

Gestão de segredos no pipeline — sem credenciais em env vars ou logs

Segredos em pipelines são um ponto cego crítico. Tokens, senhas e chaves de API costumam aparecer em lugares inesperados: variáveis de ambiente impressas em logs, arquivos .env commitados, ou segredos passados como argumentos de linha de comando visíveis no histórico do processo.

Onde segredos vazam em pipelines

Vetores comuns de exposição:

1. Código-fonte:
   API_KEY = "sk-prod-abc123..."     # hardcoded no arquivo Python
   password: "admin123"              # em docker-compose.yml commitado

2. Variáveis de ambiente impressas em log:
   env | grep -i key                 # debug casual que vira log permanente
   echo "Connecting to $DB_PASSWORD" # intenção inocente, efeito fatal

3. Histórico do git:
   git log -p | grep -i password     # segredo removido mas ainda no histórico

4. Argumentos de linha de comando:
   docker run -e DB_PASS=secret123   # visível em ps aux de outros processos

5. Artefatos de build:
   Dockerfile com ARG SECRET=xxx     # baked na layer da imagem

Detecção: scan de segredos no pipeline

Gitleaks

# GitHub Actions — gitleaks no PR
jobs:
  secrets-scan:
    runs-on: ubuntu-latest
    steps:
      - uses: actions/checkout@v4
        with:
          fetch-depth: 0   # histórico completo para detectar segredos antigos
      - name: Gitleaks scan
        uses: gitleaks/gitleaks-action@v2
        env:
          GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}

Trufflehog

# scan do repositório incluindo histórico
trufflehog git file://. --only-verified

Armazenamento correto: vaults e stores dedicados

Nunca:
  - .env commitado (mesmo em repositório privado)
  - Variável de ambiente no YAML do pipeline com valor literal
  - Segredo em comentário "temporário"

Sempre:
  - GitHub Actions Secrets / GitLab CI Variables (masked + protected)
  - AWS Secrets Manager / SSM Parameter Store
  - HashiCorp Vault
  - Azure Key Vault / GCP Secret Manager

Exemplo: segredo injetado pelo GitHub Actions (correto)

jobs:
  deploy:
    runs-on: ubuntu-latest
    steps:
      - name: Deploy
        env:
          DB_PASSWORD: ${{ secrets.DB_PASSWORD }}  # jamais o valor literal
          API_KEY: ${{ secrets.PROD_API_KEY }}
        run: ./deploy.sh

Exemplo: buscar segredo do AWS Secrets Manager no runtime

      - name: Get secret from AWS
        uses: aws-actions/aws-secretsmanager-get-secrets@v2
        with:
          secret-ids: |
            prod/myapp/db-credentials
          parse-json-secrets: true
        # injeta DB_USERNAME e DB_PASSWORD como variáveis de ambiente
        # sem expor o valor no YAML do pipeline

Prevenção de vazamento em logs

# Nunca imprima variáveis de ambiente em debug de pipeline
# Ruim:
set -x   # ativa xtrace: imprime cada comando executado com valores

# Melhor: ative xtrace só onde necessário e desative antes de usar segredos
set +x
./script-que-usa-secrets.sh
set -x
No GitHub Actions, qualquer valor definido em secrets
é automaticamente mascarado nos logs: aparece como ***.
Mas se o segredo for atribuído a uma variável intermediária
e depois impresso, o mascaramento pode falhar.
Regra: nunca faça echo de variáveis que derivam de segredos.

Rotação e auditoria

Boas práticas de ciclo de vida de segredos:

1. Rotação automática: AWS Secrets Manager rotaciona RDS/Redshift nativamente
2. TTL curto: tokens de acesso temporário (AWS STS AssumeRole) em vez de chaves fixas
3. Escopo mínimo: segredo tem acesso só ao que precisa
4. Auditoria: quem acessou o segredo e quando (CloudTrail, Vault audit log)
5. Detecção de vazamento: GitHub Secret Scanning, GitGuardian monitoram repositórios

Resumo

Credencial em pipeline é como senha em post-it: todo mundo que tem acesso ao log ou ao repositório pode ver. Use vaults, injete segredos no runtime, nunca os imprima, e escanei o histórico regularmente. Rotação automática elimina o risco de credenciais comprometidas que ficam válidas por anos.