Continuous Terraform drift detection, reporting, and auto-remediation CLI
Project description
tfdrift
Continuous Terraform drift detection, reporting, and auto-remediation.
tfdrift is a Python CLI tool that monitors your Terraform-managed infrastructure for drift — changes made outside of Terraform workflows (console clicks, scripts, other tools). It scans your Terraform workspaces, detects discrepancies between state and reality, generates structured reports, and optionally auto-remediates or notifies your team.
Why tfdrift? The most popular open-source drift detection tool (driftctl) has been in maintenance mode since mid-2023. Enterprise solutions like Terraform Enterprise cost $15K+/year. tfdrift fills the gap: a free, modern, actively maintained CLI that does one thing well.
Features
- Multi-workspace scanning — Recursively discovers all Terraform workspaces in a directory tree
- Structured drift reports — JSON, Markdown, or human-readable table output
- Severity classification — Categorizes drift by risk level (critical/high/medium/low) based on resource type and attribute
- Slack & webhook notifications — Get alerted the moment drift is detected
- Auto-remediation — Optionally run
terraform applyto fix drift (with safety guards) - CI/CD friendly — Exit codes, JSON output, and GitHub Actions integration out of the box
- Watch mode — Continuously monitor for drift on a schedule
- Ignore rules — Filter out known/expected drift with
.tfdriftignore
Quick start
Install
pip install tfdrift
Scan for drift
# Scan current directory for all Terraform workspaces
tfdrift scan
# Scan a specific directory
tfdrift scan --path /path/to/terraform
# Output as JSON
tfdrift scan --format json
# Output as Markdown report
tfdrift scan --format markdown --output drift-report.md
Watch mode (continuous monitoring)
# Check every 30 minutes, notify Slack on drift
tfdrift watch --interval 30m --slack-webhook https://hooks.slack.com/services/XXX
Auto-remediate
# Auto-fix drift in dev (requires --confirm for safety)
tfdrift scan --auto-fix --confirm --env dev
# Dry run — show what would be fixed
tfdrift scan --auto-fix --dry-run
Configuration
Create a .tfdrift.yml in your project root:
# .tfdrift.yml
scan:
paths:
- ./infrastructure
- ./modules
exclude:
- "**/test/**"
- "**/.terraform/**"
severity:
critical:
- aws_security_group.*.ingress
- aws_iam_policy.*.policy
- aws_s3_bucket.*.acl
high:
- aws_instance.*.instance_type
- aws_rds_instance.*.engine_version
notifications:
slack:
webhook_url: ${SLACK_WEBHOOK_URL}
channel: "#infra-alerts"
min_severity: high
webhook:
url: ${WEBHOOK_URL}
method: POST
remediation:
auto_fix: false
allowed_environments:
- dev
- staging
require_approval: true
max_changes: 5 # safety limit
ignore:
# Ignore expected drift
- resource: aws_autoscaling_group.*
attribute: desired_capacity
- resource: aws_ecs_service.*
attribute: desired_count
Ignore rules
Create a .tfdriftignore file to skip known drift:
# Autoscaling changes are expected
aws_autoscaling_group.*.desired_capacity
aws_ecs_service.*.desired_count
# Tags managed by external system
*.tags.LastModified
*.tags.UpdatedBy
CI/CD Integration
GitHub Actions
# .github/workflows/drift-check.yml
name: Terraform Drift Check
on:
schedule:
- cron: '0 */6 * * *' # Every 6 hours
workflow_dispatch:
jobs:
drift-check:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v4
- uses: hashicorp/setup-terraform@v3
- uses: actions/setup-python@v5
with:
python-version: '3.11'
- run: pip install tfdrift
- run: tfdrift scan --format json --output drift-report.json
env:
AWS_ACCESS_KEY_ID: ${{ secrets.AWS_ACCESS_KEY_ID }}
AWS_SECRET_ACCESS_KEY: ${{ secrets.AWS_SECRET_ACCESS_KEY }}
- uses: actions/upload-artifact@v4
if: failure()
with:
name: drift-report
path: drift-report.json
GitLab CI
drift-check:
image: python:3.11
before_script:
- pip install tfdrift
- apt-get update && apt-get install -y terraform
script:
- tfdrift scan --format json --output drift-report.json
rules:
- if: $CI_PIPELINE_SOURCE == "schedule"
artifacts:
paths:
- drift-report.json
when: on_failure
Exit codes
| Code | Meaning |
|---|---|
| 0 | No drift detected |
| 1 | Drift detected |
| 2 | Error during scan |
| 3 | Drift detected and auto-remediated |
Architecture
tfdrift/
├── commands/ # CLI command handlers (scan, watch, init)
├── detectors/ # Drift detection engine (terraform plan parser)
├── reporters/ # Output formatters (JSON, Markdown, table, Slack)
├── remediators/ # Auto-fix logic with safety guards
├── config.py # Configuration loader (.tfdrift.yml)
├── models.py # Data models (DriftResult, Resource, etc.)
├── severity.py # Severity classification engine
└── cli.py # CLI entry point (Click)
Comparison with alternatives
| Feature | tfdrift | driftctl (archived) | terraform plan | Terraform Enterprise |
|---|---|---|---|---|
| Active maintenance | ✅ | ❌ (since 2023) | ✅ | ✅ |
| Multi-workspace scan | ✅ | ❌ | ❌ | ✅ |
| Severity classification | ✅ | ❌ | ❌ | ❌ |
| Auto-remediation | ✅ | ❌ | ❌ | ✅ |
| Slack/webhook alerts | ✅ | ✅ | ❌ | ✅ |
| Watch mode | ✅ | ❌ | ❌ | ✅ |
| Ignore rules | ✅ | ✅ | ❌ | ❌ |
| Cost | Free | Free | Free | $15K+/yr |
| Language | Python | Go | Go (HCL) | Proprietary |
Contributing
Contributions are welcome! Please see CONTRIBUTING.md for guidelines.
# Development setup
git clone https://github.com/sudarshan8417/tfdrift.git
cd tfdrift
python -m venv venv
source venv/bin/activate
pip install -e ".[dev]"
pytest
License
Apache License 2.0 — see LICENSE for details.
Acknowledgments
Inspired by driftctl and the Terraform community's need for maintained, open-source drift detection tooling.
Project details
Release history Release notifications | RSS feed
Download files
Download the file for your platform. If you're not sure which to choose, learn more about installing packages.
Source Distribution
Built Distribution
Filter files by name, interpreter, ABI, and platform.
If you're not sure about the file name format, learn more about wheel file names.
Copy a direct link to the current filters
File details
Details for the file tfdrift-0.1.0.tar.gz.
File metadata
- Download URL: tfdrift-0.1.0.tar.gz
- Upload date:
- Size: 22.8 kB
- Tags: Source
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.2.0 CPython/3.13.1
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
d49cc3075b52fb35b12d7b63ac0015894e25e497e1f5a17b6970bcafe4286f2d
|
|
| MD5 |
78013caafeb9d109e174a10cc7ccc80a
|
|
| BLAKE2b-256 |
c2b4a372e52277a6fe657bd10087248bfe241c1379a96607ee7e41d544eb0b19
|
File details
Details for the file tfdrift-0.1.0-py3-none-any.whl.
File metadata
- Download URL: tfdrift-0.1.0-py3-none-any.whl
- Upload date:
- Size: 21.3 kB
- Tags: Python 3
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.2.0 CPython/3.13.1
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
4735add72e31f57df3975bb5ca43c46d6ad93e1bd43d779571d5cd8dfff82094
|
|
| MD5 |
e59a82a6c8e1f123f74a26f157faa3f8
|
|
| BLAKE2b-256 |
6a0df5351bb34eb8142abf6aeee662bfa66fb3090515e50190d5c559fde73307
|