CloudFormation drift detection compares a stack's live resource properties with what the template expects and reports differences. It is useful but incomplete: it skips resources that do not support it, ignores properties you never set explicitly, does not descend into nested stacks, and cannot compare some properties at all.
What it checks
AWS describes a resource as drifted if any actual property value differs from the expected value, including when a property or resource has been deleted. A stack is drifted if one or more resources have drifted. Expected values come from the template and its parameters.
You can run it on stacks in CREATE_COMPLETE, UPDATE_COMPLETE, UPDATE_ROLLBACK_COMPLETE and UPDATE_ROLLBACK_FAILED states.
Blind spots
From the AWS documentation:
- Unsupported resources get a status of NOT_CHECKED.
- Only explicit properties count. CloudFormation determines drift only for values set in the template or parameters. It does not include default values. To have a property tracked, set it explicitly, even to the default.
- Nested stacks are not checked when you run drift detection on the parent. Run it on each nested stack directly.
- Cross-stack attachments. Security group ingress and egress, IAM policy attachments and similar resources can confuse results when the attached resource is in a different stack.
- KMSKeyId is never checked for drift, since keys can be referenced by multiple aliases.
- Properties that cannot be compared, such as Lambda function source code or a password the service never returns.
- False positives from defaults inside arrays, or equal but not identical values like 1024 MB and 1GB.
A clean IN_SYNC result therefore means the checked, explicitly set properties match. It does not mean nothing changed.
Making it more useful for security
- Set security relevant properties explicitly in templates, such as public access settings and encryption flags, so they are tracked.
- Run drift detection on a schedule, including on nested stacks.
- Alert on MODIFIED and DELETED resource statuses, and review the property differences.
- Give the detection role read access to each resource type, plus the CloudFormation drift actions.
- Track NOT_CHECKED resources as an inventory gap and cover them another way.
Resolving drift
AWS suggests either updating the live resource to agree with the template, or importing to bring the stack in line with reality. Decide which side is right first. Sometimes an emergency console change was correct and the template is out of date. Other times it was a mistake or a hostile change.
Either way, find out who made the change. CloudTrail records the API calls, which is why AWS recommends enabling it.
A complementary view
Drift detection answers what differs from your template. It does not tell you about resources created outside CloudFormation. An asset inventory fills that gap, and Safeguard's asset discovery is built for that kind of visibility.
Click through it at your own pace, or open it full screen.
Quick check
If a stack shows IN_SYNC, is every resource in it as the template says?
Only for supported resources and explicitly set properties. Unsupported resources show NOT_CHECKED and defaults are not tracked.
Does drift detection find resources made outside CloudFormation?
No. It checks resources that belong to the stack. Use an inventory or discovery tool for unmanaged resources.
Sources
- Detect unmanaged configuration changes with drift detection (AWS CloudFormation)
- Security best practices for CloudFormation (AWS)
Last reviewed: 19 October 2026.