Terraform State Puzzle
Fix broken Terraform state without destroying production. Eight puzzles with real Terraform output: a rename that would replace a database, an import that forces replacement, a stale lock, drift, count index shifts and more. Choose between moved, import and removed blocks and the state commands.
Category: DevOps
What You Will Learn
- Rename or refactor Terraform resources with moved blocks instead of destroying them
- Adopt existing infrastructure with import blocks, and read the import plan before you apply
- Stop managing a resource without deleting it, with a removed block and destroy = false
- Clear a stale state lock with terraform force-unlock, only after checking nobody is running
- Handle drift: what terraform plan -refresh-only and apply -refresh-only really change
- Fix count index shifts by moving to for_each with moved blocks
- Recognise a plan that reads the wrong workspace or state
Topics covered: terraform, terraform-state, moved-block, import-block, removed-block, force-unlock, iac, infrastructure-as-code, troubleshooting, interactive, educational
// simulator
Terraform State Puzzle
Fix broken Terraform state without destroying production. Eight puzzles with real Terraform output: a rename that would replace a database, an import that forces replacement, a stale lock, drift, count index shifts and more. Choose between moved, import and removed blocks and the state commands.
Plan wants to build production again
Each puzzle is a broken Terraform situation from a real team. Read the plan and the code, run read-only checks for free, then choose a fix. A wrong pick shows what Terraform would do, and you try again.
You cloned the platform repo on a new laptop this morning and ran terraform init. Now terraform plan wants to create all of production, which is up and serving traffic. The team keeps one workspace per environment in the S3 backend, and CI selects the right one itself.
Goal: Get a plan against the real production state that shows no changes, without touching AWS.
What the plan does now2 resources
Terraform links an address in the code to an entry in the state, and the state entry to a real object. State (workspace "default").
- create
- Code
- aws_db_instance.primary
- State
- (none)
- AWS
- acme-prod-db (in prod state)
- create
- Code
- aws_vpc.main
- State
- (none)
- AWS
- vpc-0a1b2c3d (in prod state)
Read-only checks. They are free and the answer opens in Evidence.
All command output was recorded with Terraform 1.15.8 using local stand-in resources, then relabelled to look like AWS. Plan headers, symbols, warnings, errors and summaries are what Terraform printed; resource bodies are trimmed to the attributes that matter.
About the Terraform State Puzzle
What you'll practise
- Reading a plan for the one line that matters: destroy, replace, or move
- Choosing between moved, import and removed blocks and their command-line versions
- Telling state, code and real infrastructure apart, and which one Terraform trusts
- Clearing a stale lock without trampling a run that is still alive
- Cleaning up after an apply that was killed halfway
- Refactoring count to for_each without replacing anything
How it works
- Eight puzzles: each one is a broken situation with the code, the plan, and the state or error a team would see.
- Free checks: read-only commands such as terraform state list show more evidence before you decide.
- Four kinds of answer: the best fix, a fix that works with a catch, a safe step that does not finish the job, and an unsafe one. Wrong picks show what Terraform would do.
- Real output: every transcript was recorded with Terraform 1.15.8, using local stand-in resources relabelled as AWS.
Prefer blocks in code to state commands
Since Terraform 1.1 (moved), 1.5 (import) and 1.7 (removed), most state surgery can be written as code. The change shows up in the plan, goes through review with the rest of the pull request, and applies to every state that uses the configuration. The old commands, terraform state mv, terraform import and terraform state rm, still work, but they change the state at once, outside that flow.
Read more
New to Terraform? Start with the Terraform Basics Simulator, which covers init, plan, apply and destroy. For the commands behind these puzzles, read how to remove, move and migrate Terraform state and how to unlock a locked state file, or the state management chapter of our Terraform guide.
Overview
Most Terraform trouble is not about writing resources, it is about state: what Terraform thinks exists compared with what really does. This puzzle game gives you real situations to untangle. A plan wants to build production again because you are in the wrong workspace. A tidy-up rename makes Terraform want to destroy and recreate a database. Someone deleted an alarm by hand. A state lock will not go away. An apply was killed halfway. A database built by hand needs to be adopted, and staging has to be retired without touching production. For each one you inspect the evidence, such as the workspace list, the state, the plan and the pull request diff, then pick a fix. Answers are graded as the best fix, a fix that works with a catch, a safe step that does not finish the job, or an unsafe action that does damage, and you see the plan each choice would produce. The recurring lesson is to prefer declarative blocks in code, such as moved, import and removed, over one-off state commands, so the fix is reviewed and repeatable.
Try this
- Open "Plan wants to build production again" and check which workspace you are in before you apply anything.
- Solve "The tidy-up rename" with a moved block and compare it with simply applying the plan.
- Try "Adopt the hand-made database" and see why an import is safer than letting Terraform create a new one.
Frequently asked questions
- What does a moved block do in Terraform?
- It tells Terraform that a resource address changed, for example after a rename or a move into a module, so it updates the state instead of destroying the old resource and creating a new one.
- How do I bring an existing resource under Terraform management?
- Use an import block in your configuration (Terraform 1.5 and later) or terraform import, with matching resource code. Then plan to confirm there are no unexpected changes.
- What should I do about a stuck Terraform state lock?
- First make sure no other run is actually in progress. Only then remove it with terraform force-unlock and the lock ID, because breaking a lock during a real apply can corrupt the state.
Try next
// simulator
Preview Environment Simulator
See how a pull request becomes a temporary copy of your app, complete with a private URL, safe test data, review checks, and automatic cleanup.
// game
Heroku-Style Name Generator
Generate names the way Heroku, Docker, Kubernetes, and petname do, see how the word lists combine, and learn when the birthday problem makes random names collide.
// simulator
How Docker Works Under the Hood
Watch what really happens when you run docker run -p 8080:80 nginx, one layer at a time. Step down the whole stack: the CLI, the daemon, the registry pull, containerd, the OCI runtime bundle, runc, the running container, and the shared Linux kernel. Every stage shows the real low-level command you can run yourself, so it doubles as a tour of the primitives that make a container: namespaces, cgroups, and runc. A container is not a small VM, and this shows you why.