"ClickOps" is the affectionate, slightly accusatory name for building cloud infrastructure by clicking through the console. It's how almost everything starts, because it's the fastest way to get something live. The problem isn't the first click — it's the hundredth, when no one can say what's running, why a security group has that rule, or how to rebuild the account if a region goes dark. This is a staged playbook for getting out of that hole and into Infrastructure as Code, without a risky big-bang rewrite.
- What ClickOps actually costs you
- The core principle: codify, don't recreate
- Stage 1 — Inventory
- Stage 2 — Prioritise
- Stage 3 — Codify in slices
- Stage 4 — Reconcile state
- Stage 5 — Lock the console down
- FAQ
What ClickOps actually costs you
Console-built infrastructure is invisible in four ways that compound over time:
- No documentation. The only record of a resource is the resource itself. Intent — why a thing exists — lives in someone's memory, or nowhere.
- No reproducibility. Rebuilding for DR, a new region, or a fresh staging environment means re-clicking from scratch and hoping you match.
- No review. A change to a production security group takes two clicks and zero approvals. That's a security and reliability liability.
- No drift baseline. Without code, there's nothing to compare reality against — so you can't even tell when something changed.
IaC fixes all four, but only if you migrate the existing estate. A green-field Terraform repo that ignores the 300 resources already running just adds a second source of truth.
The core principle: codify, don't recreate
The golden rule of brownfield migration: never let Terraform recreate a resource that already exists. Bind to it, don't rebuild it.
This is the single idea that makes the whole migration safe. You are describing live resources in code and binding Terraform's state to them — not asking Terraform to create new ones. Done right, your first terraform apply after import reports no changes. If it wants to create, replace, or destroy anything, your code doesn't yet match reality and you stop and fix it before proceeding.
Stage 1 — Inventory
You can't codify what you can't see. Build a complete picture of what's actually running, region by region: VPCs and subnets, security groups, EC2 and load balancers, RDS, S3, IAM roles and policies, Lambda, and the rest. The AWS console, Config, and Resource Groups help, but they're tedious to assemble into something usable.
This is where an automated read-only scan saves days. InfraSync enumerates 87+ AWS services and produces the inventory and the Terraform for it in one pass — see our guide to generating Terraform from AWS for the full menu of tools, including the open-source options.
Stage 2 — Prioritise
Don't codify alphabetically. Sequence by risk and value:
- Networking first. VPCs, subnets, route tables, and security groups are the foundation everything else references. Capture them first so later resources can point at them.
- Stateless, high-change next. Compute, load balancers, and Lambda change often and benefit most from review.
- Stateful, sensitive last. Databases and anything with data attached. Codify these carefully, once you trust your workflow.
- Defer the throwaway. Resources slated for deletion don't need codifying — note them and move on.
Stage 3 — Codify in slices
Work in small, reviewable slices — one service or one VPC at a time — each landing as its own pull request. A slice is done when the generated HCL is cleaned up (defaults pruned, hard-coded IDs replaced with references, resources grouped into modules) and a teammate has reviewed it.
Resist the urge to codify the whole account in one heroic branch. Small slices keep reviews meaningful, make rollback trivial, and let the team learn the workflow before the stakes get high.
Stage 4 — Reconcile state
For each slice, bind the code to live resources and prove the match:
# Bind existing resources into state, then:
terraform plan
# The only acceptable result for a codification slice:
# No changes. Your infrastructure matches the configuration.
If the plan proposes changes, your code differs from reality. Common culprits: missing tags, default values you didn't capture, or attributes managed elsewhere. Fix the code until the plan is clean. A no-op plan is your proof of a faithful migration.
Stage 5 — Lock the console down
Codification only sticks if new ClickOps stops sneaking in. As each area comes under Terraform, tighten IAM so humans lose write access to it in the console; changes now flow exclusively through pull requests. Keep read access — the console is still the best place to look at things.
Then make divergence visible. Schedule recurring drift detection so that the moment someone makes an emergency console change, you know about it and can fold it back into code. This is the difference between a migration that holds and one that quietly rots back into ClickOps within a quarter.
Inventory and codify in one read-only pass.
InfraSync scans your live AWS account, generates the Terraform for it, and opens a GitHub PR — then re-scans on a schedule so the console can't drift away from your code. Read-only by design.
Start a free scanFAQ
What is ClickOps?
ClickOps is building and changing cloud infrastructure by clicking through a provider's web console instead of declaring it in code. It's fast to start with but produces infrastructure that's undocumented, hard to reproduce, and easy to change without review.
Do I have to stop using the AWS console to adopt IaC?
Not on day one. A realistic migration codifies the estate in stages while the console stays open, then progressively restricts console write access as each area comes under Terraform — ending with read-mostly console access and changes flowing through pull requests.
How do I migrate without downtime?
Codification causes no downtime because it only reads your account and binds existing resources into state — it doesn't recreate them. The safety check is confirming terraform plan shows no changes after import. Risk appears only when you start making changes, which you then route through reviewed pull requests.