Recuperar um state quebrado
State quebrado tem três formas: lock preso (ninguém consegue aplicar), divergência (o state não corresponde à realidade) e corrupção (o arquivo está inválido ou truncado). Cada uma tem um caminho, e todos começam do mesmo lugar.
1. Faça backup antes de qualquer coisa
Seção intitulada “1. Faça backup antes de qualquer coisa”Sem exceção, mesmo com pressa.
terraform state pull > backup-$(date +%F-%H%M%S).tfstatewc -c backup-*.tfstate # confirme que não veio vazioSe o backend for S3 com versionamento ativo (e deveria ser), você já tem uma rede de segurança adicional — o passo 4 usa isso.
2. Destrave o lock, com cuidado
Seção intitulada “2. Destrave o lock, com cuidado”terraform plan# Error: Error acquiring the state lock# ID: 8f2a... Who: ana@notebook Created: 2026-09-04 09:12Antes de forçar, confirme que nenhum apply está em execução: pergunte à pessoa indicada, e verifique se há job rodando no CI. Destravar durante um apply ativo é o caminho mais rápido para corromper o state de verdade.
terraform force-unlock 8f2a... # só depois de confirmar3. Reconcilie divergências com refresh
Seção intitulada “3. Reconcilie divergências com refresh”Quando o state não corresponde à realidade (alguém mexeu no console, um apply morreu no meio):
terraform plan -refresh-only # mostra o que mudou fora do códigoterraform apply -refresh-only # atualiza o state, sem alterar infraestruturaterraform plan # agora o plano reflete a diferença real-refresh-only só atualiza o state; ele nunca cria nem destrói. Leia cada mudança
proposta antes de aceitar.
4. Restaure uma versão anterior
Seção intitulada “4. Restaure uma versão anterior”Para corrupção ou remoção acidental, o caminho mais rápido é voltar no tempo:
aws s3api list-object-versions --bucket empresa-tfstate-prod \ --prefix loja/prod/terraform.tfstate \ --query 'Versions[:5].[VersionId,LastModified]' --output table
aws s3api get-object --bucket empresa-tfstate-prod \ --key loja/prod/terraform.tfstate --version-id <ID> restaurado.tfstate
terraform state push restaurado.tfstateterraform plan # confirme que o plano faz sentido antes de qualquer applySe o push recusar por causa do serial, é proteção contra sobrescrita: incremente o
campo serial no JSON restaurado e tente de novo — com a certeza de que ninguém mais está
aplicando.
5. Remova recurso do state sem destruí-lo
Seção intitulada “5. Remova recurso do state sem destruí-lo”Útil quando um recurso foi apagado por fora, ou vai passar para outro state.
terraform state list | grep aws_db_instanceterraform state rm aws_db_instance.legado # esquece; NÃO destrói nada na nuvem6. Reimporte o que ficou órfão
Seção intitulada “6. Reimporte o que ficou órfão”terraform import aws_s3_bucket.relatorios empresa-relatorios-prodterraform plan # o alvo continua sendo: "No changes"Para renomear um recurso no código sem recriar:
terraform state mv aws_s3_bucket.antigo aws_s3_bucket.novo# ou, melhor porque é versionado e revisável:# moved { from = aws_s3_bucket.antigo to = aws_s3_bucket.novo }7. Feche o buraco que causou isso
Seção intitulada “7. Feche o buraco que causou isso”Depois de estabilizar, ataque a causa. As recorrentes são poucas:
- Sem locking → habilite (
use_lockfileno S3, ou tabela DynamoDB). - Sem versionamento no bucket do state → ative agora; é a diferença entre dez minutos e um dia de trabalho.
- Apply da máquina de alguém → mova para o pipeline, com credencial só lá.
- State único e gigante → veja dividir um state.
- Alteração manual no console → detecção diária de drift, com alerta.
# job diário: plano não vazio vira alertaterraform plan -detailed-exitcode -lock=false || echo "drift detectado"Se der errado
Seção intitulada “Se der errado”| Sintoma | O que fazer |
|---|---|
state snapshot was created by Terraform vX |
Versão do binário mais antiga que a do state; use a mesma versão |
Failed to load state: unexpected EOF |
Arquivo truncado — restaure a versão anterior |
Duplicate resource após push |
O state restaurado tem recurso já reimportado; remova um dos dois |
| Plano quer criar o que já existe | State perdeu o recurso — reimporte |
| Plano quer destruir tudo | Provavelmente você está no diretório ou workspace errado. Pare. |
O último merece a pausa: confirme terraform workspace show, o backend configurado e a
conta (aws sts get-caller-identity) antes de qualquer coisa.
Checklist de pronto
Seção intitulada “Checklist de pronto”- Backup do state feito antes de intervir.
- Lock liberado só após confirmar que ninguém aplica.
-
terraform planlimpo, sem criações nem destruições inesperadas. - Nenhum recurso órfão deixado para trás.
- Locking e versionamento habilitados no backend.
- Causa registrada e corrigida (pipeline, drift, divisão de state).