Skip to main content

Terraform State

·804 words·4 mins
Jack Warner
Author
Jack Warner
A little blog by me

Terraform State
#

Overview
#

When a resource is created for the very first time, Terraform creates a state file to keep track of the resources it manages. This state file is crucial for Terraform to understand the current state of the infrastructure and to plan future changes accurately.

$ ls
main.tf  variables.tf  terraform.tfstate terraform.tfstate.backup

Local State Basics
#

The state file is a JSON file that contains information about the resources Terraform manages. Terraform uses it to track the current state of infrastructure and to determine the changes required for the desired state.

If you run terraform plan, Terraform compares the current state from the state file with the desired state in configuration files and shows what changes will be made.

When you run terraform apply, Terraform applies those changes and updates the state file accordingly.

You can disable refresh during apply:

$ terraform apply -refresh=false

The state file also tracks dependencies between resources. If one resource depends on another, Terraform uses dependency information from state to plan operations correctly.

Warning: State files can contain sensitive information and should be stored in a secure backend.

Never manually edit the state file.


Remote State and State Locking
#

A state file maps configuration to real-world resources, tracks metadata, improves performance, and supports collaboration.

It is not a good idea to store state files locally long term or in version control.

If two terminals run terraform apply at the same time, Terraform locks the state so only one operation can update it at a time. This is called state locking.

To configure a remote backend, a common setup is S3 for state storage and DynamoDB for state locking.

main.tf
resource "local_file" "pet" {
	filename = "/root/pets.txt"
	content  = "We love pets!"
}
terraform.tf
terraform {
	backend "s3" {
		bucket         = "kodekloud-terraform-state-bucket01"
		key            = "finance/terraform.tfstate"
		region         = "us-west-1"
		dynamodb_table = "state-locking"
	}
}

When you run terraform init, Terraform initializes the backend and prepares state handling in S3 with locking in DynamoDB.


Backend Reinitialization Workflow
#

If you run terraform apply immediately after backend configuration changes, you can get this error:

$ terraform apply
Backend reinitialization required. Please run "terraform init". Reason: Initial configuration of the requested backend "s3"
The "backend" is the interface that Terraform uses to store state, perform operations, etc. If this message is showing up, it means
that the Terraform configuration you're using is using a custom configuration for the Terraform backend.
Changes to backend configurations require reinitialization. This allows Terraform to setup the new configuration, copy existing
state, etc. This is only done during "terraform init". Please run that command now then try again.
Error: Initialization required. Please see the error message above.

This happens because Terraform must reinitialize to use the new backend configuration.

$ terraform init
Initializing the backend...
Do you want to copy existing state to the new backend?
Pre-existing state was found while migrating the previous "local" backend to the newly configured "s3" backend. No existing state
was found in the newly configured "s3" backend. Do you want to copy this state to the new "s3"
backend? Enter "yes" to copy and "no" to start with an empty state.
Enter a value: yes
Successfully configured the backend "s3"! Terraform will automatically use this backend unless the backend configuration changes.
Initializing provider plugins...
- Using previously-installed hashicorp/aws v3.7.0
.
.[Output Truncated]

Here, the existing state is copied from the local backend to S3. After this, terraform apply works as expected.


Remote Backend Options
#

Terraform state tracks managed infrastructure and configuration. It maps real-world resources, tracks metadata, and improves performance.

Why Use Remote State Backends?
#

  • Team collaboration
  • Security
  • Reliability

Types of Remote State Backends
#

  • S3 Backend: Stores state as a JSON file in S3, with DynamoDB for locking.
  • AzureRM Backend: Stores state in Azure Blob Storage, with Azure Cosmos DB for locking.
  • GCS Backend: Stores state in Google Cloud Storage, with Cloud Spanner for locking.
  • Consul Backend: Stores state in a Consul key-value store.
  • Artifactory Backend: Stores state in a private versioned repository.
  • HCP Terraform: Formerly Terraform Cloud, fully managed by HashiCorp.

Choosing the Right Backend
#

Choose based on:

  • Integration requirements
  • Security requirements
  • Team access needs
  • Cost implications
  • Operational complexity

Dependency Lock File
#

terraform.lock.hcl ensures consistent provider versions across environments and Terraform operations.

Purpose
#

  • Consistency
  • Reproducibility
  • Compatibility assurance

How It Works
#

When you run terraform init, Terraform automatically creates .terraform.lock.hcl.

Lock File Contents
#

  • Exact provider versions
  • Provider checksums
  • Provider metadata

Best Practices
#

  • Commit the lock file to version control.
  • Regularly update providers.
  • Review lock file changes carefully.
  • Use consistent provider versions across environments.

Conclusion
#

Remote backend choice affects efficiency, security, and manageability, and helps ensure stable and predictable infrastructure deployments.

Dependency lock files help manage provider versions, guard against unintended updates, and provide a clear path for safe and intentional upgrades.

Related