terraformtfvars
Terraform tfvars Guide: Best Practices, Variables & Playbook (2025)
Terraform .tfvars files are the backbone of any production Infrastructure-as-Code deployment. They separate configuration from code, enabling reusable modules across environments. Yet many teams misuse them — hardcoding secrets, neglecting naming conventions, or skipping validation entirely.
This playbook gives you everything you need to manage .tfvars files correctly, from basics to advanced patterns used by mature platform teams.
Key Takeaways
- Variable precedence matters: Command-line
-var-fileoverrides file defaults — order determines final values. - Never commit secrets to version control: Use
.gitignore, remote state backends with encryption, or secret managers. - Environment isolation is non-negotiable: One
.tfvarsper environment (dev, staging, prod) prevents accidental cross-contamination. - Validate before apply: Run
terraform validateand useterraform planto audit variable values before any infrastructure change. - Use
terraform.tfvars.jsonfor complex data: JSON-format tfvars support nested objects and arrays that HCL syntax cannot express cleanly.
What Are Terraform .tfvars Files?
Definition and Purpose
A .tfvars file (Terraform Variables) defines values for input variables declared in your Terraform configuration. They live outside .tf files so that environment-specific values can change without modifying source code.
How Terraform Resolves Variable Values
Terraform resolves variable values through a defined precedence hierarchy:
- Explicit
-varflags on the command line (highest priority) .tfvarsfiles loaded via-var-file(loaded in order; later files override earlier ones)- The default auto-loaded
terraform.tfvarsorterraform.tfvars.json - Variables set in
.tfdeclaration blocks via thedefaultattribute - Environment variables prefixed with
TERRAFORM_VAR_ - Unset variables with no default raise an error (lowest — fails loud)
Terraform tfvars Naming Conventions
Consistent naming is the single most impactful practice for scalable Terraform projects. Here is the industry-standard convention:
| File Name | Purpose | Loaded Automatically? |
|---|---|---|
terraform.tfvars |
Default fallback values for all environments | Yes — loaded automatically by Terraform |
terraform.tfvars.json |
Same as above but in JSON format (supports complex types) | Yes — loaded automatically by Terraform |
dev.tfvars |
Development environment overrides | No — must be passed via -var-file |
staging.tfvars |
Staging environment overrides | No — must be passed via -var-file |
prod.tfvars |
Production environment overrides | No — must be passed via -var-file |
secrets.tfvars |
Sensitive values (never committed to VCS) | No — must be passed via -var-file |
Practical tfvars Playbook
Step 1 — Declare Variables in .tf Files
Every .tfvars value must have a corresponding variable declaration. Never rely on implicit variables.
variable "instance_type" {
type = string
default = "t3.micro"
description = "EC2 instance type for the application server"
}
variable "environment" {
type = string
default = "dev"
validation {
condition = contains(["dev", "staging", "prod"], var.environment)
error_message = "Environment must be dev, staging, or prod."
}
}
Step 2 — Create Environment-Specific .tfvars Files
- Create
dev.tfvarswith development-appropriate values - Create
staging.tfvarsmirroring prod structure with scaled-down resources - Create
prod.tfvarswith production-grade configurations - Keep all files aligned in variable keys — missing keys fall back to defaults
Step 3 — Run Terraform with Explicit -var-file Flags
# Development deploy
terraform apply -var-file="dev.tfvars"
# Staging deploy
terraform apply -var-file="staging.tfvars"
# Production deploy with explicit confirmation
terraform apply -var-file="prod.tfvars" -auto-approve
Step 4 — Protect Sensitive Variables
- Declare sensitive variables with
sensitive = true - Store sensitive
.tfvarsfiles in.gitignore - Use a secrets manager (AWS Secrets Manager, HashiCorp Vault) for CI/CD pipelines
- Never print variable values in logs — mark them sensitive in declarations
Step 5 — Validate and Audit Before Every Apply
- Run
terraform validateto catch syntax and type errors - Run
terraform plan -var-file="prod.tfvars"to review all proposed changes - Use
terraform fmt -checkto enforce formatting standards in CI - Use
terraform tflintto catch common anti-patterns
Common tfvars Anti-Patterns to Avoid
| Anti-Pattern | Problem | Better Approach |
|---|---|---|
| Hardcoding secrets in .tfvars | Accidental commit to VCS exposes credentials | Use remote state + secret managers; add secrets.tfvars to .gitignore |
| Single monolithic .tfvars for all envs | Changes intended for one environment affect all | One file per environment with explicit -var-file flags |
| No variable type constraints | Runtime errors and silent misconfigurations | Always declare type and use validation blocks |
| Skipping terraform validate | Errors only surface during apply, wasting time and risking drift | Integrate validate into CI pipeline before plan and apply steps |