- Detect provider-side changes (drift) using
terraform plan -refresh-only - Choose whether to enforce configuration or accept external changes into state
- Update Terraform configuration to keep code and real-world resources in sync
Example Terraform configuration
Below is a minimal Terraform configuration that creates an AWS VPC, a subnet, and an EC2 instance used as a web server:This snippet omits the
cidr_block on aws_subnet for brevity. In production, aws_subnet requires a valid cidr_block and usually an availability_zone. Always specify those values in real deployments.
Simulate an out-of-band change
Sometimes changes are made directly in the cloud provider (manually or by another team). For this demo:- Stop the EC2 instance in the AWS Console.
- Change its instance type from
t2.smalltot3.small. - Add a new tag:
Team = dev-app-01. - Start the instance again.


t3.small) and save.

Detecting drift with Terraform
To detect changes made outside of Terraform, run a refresh-only plan. This command refreshes resource attributes from the provider and reports differences between the refreshed state and the configuration without proposing changes to infrastructure:-refresh-only:
instance_typechanged fromt2.smalltot3.small.- A new tag
Team = dev-app-01appears. - Some attributes (e.g.,
ebs_optimized, CPU/thread counts) can change when switching instance families — these are provider-driven differences.
Two ways to resolve detected drift
You have two primary options after detecting drift. The best choice depends on whether you want configuration to be the source of truth or whether you want to accept the out-of-band changes.| Option | Action | Command | Outcome |
|---|---|---|---|
| Revert provider to match configuration | Make real infrastructure match Terraform code (configuration is source of truth) | terraform apply | Terraform will modify resources to match your configuration (may restart/replace resources). |
| Accept provider changes into state | Update Terraform state to reflect current provider attributes without changing infrastructure | terraform apply -refresh-only | Terraform updates the state file only; no provider-side changes are made. |
- Revert manual changes to match Terraform (enforce code)
- Run a regular apply to make real resources match your configuration:
instance_type and removes tags not present in your code.
- Accept manual changes into Terraform state (no infra changes)
- Use the apply refresh-only option to update state to match the provider:
yes to accept.

Keep configuration and state in sync
If you accepted the provider-side changes into state and want those changes to persist, update your Terraform configuration accordingly:- Update the
instance_typevariable default:
- Add the new
Teamtag to the resource’stagsblock:
Use
terraform plan -refresh-only to detect drift. To accept external changes into state without modifying resources, use terraform apply -refresh-only. To make real infrastructure match your code (configuration as source of truth), run a normal terraform apply.