Terraform Advanced — null_resource Escape Hatch
When Terraform doesn’t support what you need, null_resource and terraform_data fill the gap.
null_resource + local-exec
resource "null_resource" "db_setup" {
triggers = {
db_endpoint = aws_db_instance.main.endpoint
schema_hash = filemd5("${path.module}/schema.sql")
}
provisioner "local-exec" {
command = "psql -h ${aws_db_instance.main.address} -f schema.sql"
environment = {
PGPASSWORD = var.db_password
}
}
}
Re-runs when DB endpoint changes or schema file is modified.
terraform_data (Terraform 1.4+)
The modern replacement for null_resource:
resource "terraform_data" "bootstrap" {
triggers_replace = [aws_instance.app.id]
provisioner "remote-exec" {
inline = ["sudo systemctl restart app"]
connection {
host = aws_instance.app.public_ip
user = "ec2-user"
}
}
}
Common Use Cases
✅ Run a script after resource creation
✅ Trigger actions on dependency changes
✅ Wait for external process to complete
✅ Seed databases or configure third-party tools
Anti-Pattern Warning
# ❌ Don't use null_resource for everything
# If there's a proper Terraform resource, use it instead
# ❌ Bad
resource "null_resource" "s3_bucket" {
provisioner "local-exec" {
command = "aws s3 mb s3://my-bucket"
}
}
# ✅ Good
resource "aws_s3_bucket" "my_bucket" {
bucket = "my-bucket"
}
💡 Production Tip:
null_resourceandterraform_datashould be your last resort. Always check if a proper Terraform resource or data source exists first.
What’s Next?
Practice production patterns.