Kuasai Terraform state management dengan remote backend, locking, dan versioning. Pelajari production-grade strategy untuk prevent infrastructure disaster dan keep IaC Anda reliable pada scale.

Terraform state adalah source of truth untuk infrastruktur Anda. Ini juga file paling dangerous yang akan Anda manage. Kehilangan, corrupt, atau biarkan multiple people edit secara bersamaan, dan Anda sedang melihat infrastructure chaos—resource dihapus secara unexpected, duplicate resource dibuat, atau lebih buruk, seluruh production environment Anda menjadi unmanageable.
Sebagian besar team mulai dengan local state file selama development. Itu bekerja baik sampai Anda hit production. Kemudian realitas hit: Anda memerlukan multiple people managing infrastructure, Anda perlu prevent concurrent modification, Anda perlu audit trail, dan Anda perlu state Anda survive laptop crash.
Panduan ini mencakup production-grade state management strategy yang prevent disaster sebelum mereka terjadi.
Terraform state adalah file JSON yang map infrastructure code Anda ke real resource dalam cloud provider Anda. Ketika Anda run terraform apply, Terraform:
Tanpa state, Terraform tidak memiliki cara untuk mengetahui apa yang sebelumnya dibuat. Tidak dapat track resource ID, tidak dapat detect drift, dan tidak dapat safely update atau destroy resource.
Local state file hidup di mesin Anda. Ini membuat beberapa problem:
Collaboration breaks down. Ketika dua engineer run terraform apply dari mesin berbeda, mereka bekerja dengan state file berbeda. Perubahan orang kedua mungkin overwrite orang pertama, atau lebih buruk, keduanya mungkin coba modify resource yang sama secara bersamaan.
State hilang. Laptop Anda mati, hard drive Anda gagal, atau Anda accidentally delete file. Sekarang Anda tidak memiliki record apa yang Terraform buat, dan Anda tidak dapat safely manage resource itu lagi.
Tidak ada audit trail. Anda tidak dapat lihat siapa yang ubah apa, kapan, atau mengapa. Ini violate compliance requirement dan membuat debugging infrastructure issue hampir impossible.
Concurrent modification menyebabkan corruption. Jika dua orang run Terraform pada waktu yang sama, state file dapat menjadi corrupt atau inconsistent.
Remote backend menyimpan state file Anda pada centralized server daripada local machine Anda. Terraform membaca dan menulis state melalui API, yang berarti:
AWS S3 dengan DynamoDB adalah most common choice untuk AWS-based infrastructure. S3 menyimpan state file, dan DynamoDB menyediakan state locking.
Terraform Cloud (managed oleh HashiCorp) menangani semua complexity untuk Anda. Ini adalah SaaS solution dengan built-in state management, locking, dan team collaboration feature.
Azure Storage Account bekerja baik jika Anda dalam Azure ecosystem.
Google Cloud Storage adalah natural choice untuk GCP deployment.
Consul berguna jika Anda sudah running Consul untuk service discovery.
Untuk panduan ini, kami akan focus pada S3 + DynamoDB karena widely used dan memberikan Anda full control.
Anda perlu membuat S3 bucket dan DynamoDB table sebelum Terraform dapat menggunakannya. Ini adalah chicken-and-egg problem: Anda memerlukan infrastructure untuk menyimpan infrastructure code state Anda.
Solusinya adalah membuat resource ini secara manual atau dengan separate Terraform configuration yang menggunakan local state (hanya kali ini).
aws s3api create-bucket \
--bucket my-terraform-state \
--region us-east-1 \
--create-bucket-configuration LocationConstraint=us-east-1Setelah backend infrastructure ada, konfigurasi Terraform untuk menggunakannya:
terraform {
backend "s3" {
bucket = "my-terraform-state"
key = "prod/terraform.tfstate"
region = "us-east-1"
dynamodb_table = "terraform-locks"
encrypt = true
}
}Parameter key menentukan di mana state file Anda hidup dalam bucket. Menggunakan path seperti prod/terraform.tfstate memungkinkan Anda organize multiple environment dalam satu bucket.
Ketika Anda run terraform init dengan new backend configuration, Terraform bertanya apakah Anda ingin migrate existing state Anda:
terraform initDo you want to copy existing state to the new backend?Jawab yes, dan Terraform secara otomatis upload local state Anda ke S3 dan update configuration Anda untuk menggunakan remote backend.
Important
Setelah migration, hapus local terraform.tfstate dan terraform.tfstate.backup file Anda. Mereka tidak lagi diperlukan dan pose security risk jika mereka contain sensitive data.
State locking prevent dua Terraform operation dari running secara bersamaan. Tanpa itu, scenario ini terjadi:
terraform apply dan mulai modify resourceterraform apply sebelum A selesaiDengan locking, B operation menunggu sampai A lock dirilis.
Ketika Terraform acquire lock, itu membuat entry dalam DynamoDB table dengan:
LockID: Unique identifier untuk lock iniInfo: Metadata tentang siapa yang hold lock dan mengapaDigest: Hash dari state file untuk detect corruptionOperation: Operation yang dilakukan (apply, destroy, dll)Who: User yang menjalankan operationVersion: Terraform versionCreated: Ketika lock di-acquireJika Terraform crash atau hang, lock tetap dalam DynamoDB. Anda dapat manually release jika diperlukan:
aws dynamodb scan --table-name terraform-locksaws dynamodb delete-item \
--table-name terraform-locks \
--key '{"LockID":{"S":"my-terraform-state/prod/terraform.tfstate"}}'Warning
Hanya release lock secara manual jika Anda absolutely certain operation yang acquire itu telah berhenti. Releasing active lock dapat menyebabkan state corruption.
S3 dapat encrypt state file Anda secara otomatis. Aktifkan server-side encryption:
aws s3api put-bucket-encryption \
--bucket my-terraform-state \
--server-side-encryption-configuration '{
"Rules": [{
"ApplyServerSideEncryptionByDefault": {
"SSEAlgorithm": "AES256"
}
}]
}'Atau gunakan KMS untuk lebih banyak control:
aws s3api put-bucket-encryption \
--bucket my-terraform-state \
--server-side-encryption-configuration '{
"Rules": [{
"ApplyServerSideEncryptionByDefault": {
"SSEAlgorithm": "aws:kms",
"KMSMasterKeyID": "arn:aws:kms:us-east-1:123456789012:key/12345678-1234-1234-1234-123456789012"
}
}]
}'Selalu gunakan HTTPS saat mengakses S3. Terraform melakukan ini secara default, tetapi verify AWS CLI configuration Anda:
aws s3api get-bucket-policy --bucket my-terraform-stateTambahkan bucket policy untuk deny unencrypted upload:
{
"Version": "2012-10-17",
"Statement": [
{
"Sid": "DenyUnencryptedObjectUploads",
"Effect": "Deny",
"Principal": "*",
"Action": "s3:PutObject",
"Resource": "arn:aws:s3:::my-terraform-state/*",
"Condition": {
"StringNotEquals": {
"s3:x-amz-server-side-encryption": "AES256"
}
}
}
]
}Restrict siapa yang dapat read dan modify state file Anda. Gunakan IAM policy:
resource "aws_iam_policy" "terraform_state" {
name = "terraform-state-access"
policy = jsonencode({
Version = "2012-10-17"
Statement = [
{
Effect = "Allow"
Action = [
"s3:ListBucket",
"s3:GetBucketVersioning"
]
Resource = "arn:aws:s3:::my-terraform-state"
},
{
Effect = "Allow"
Action = [
"s3:GetObject",
"s3:PutObject",
"s3:DeleteObject"
]
Resource = "arn:aws:s3:::my-terraform-state/*"
},
{
Effect = "Allow"
Action = [
"dynamodb:DescribeTable",
"dynamodb:GetItem",
"dynamodb:PutItem",
"dynamodb:DeleteItem"
]
Resource = "arn:aws:dynamodb:us-east-1:123456789012:table/terraform-locks"
}
]
})
}Attach policy ini hanya ke user dan role yang perlu manage infrastructure.
S3 versioning menyimpan previous version dari state file Anda. Jika sesuatu salah, Anda dapat restore earlier version:
aws s3api put-bucket-versioning \
--bucket my-terraform-state \
--versioning-configuration Status=EnabledList semua version dari state file Anda:
aws s3api list-object-versions \
--bucket my-terraform-state \
--prefix prod/terraform.tfstateJika state file Anda menjadi corrupt, restore previous version:
aws s3api get-object \
--bucket my-terraform-state \
--key prod/terraform.tfstate \
--version-id abc123def456 \
terraform.tfstate.backupKemudian beri tahu Terraform untuk menggunakan version ini:
terraform state push terraform.tfstate.backupCaution
Hanya restore state sebagai last resort. Restore old state file dapat menyebabkan Terraform berpikir resource telah dihapus ketika mereka benar-benar masih ada, leading ke accidental destruction.
Organisir Terraform code Anda untuk keep environment terpisah:
terraform/
├── environments/
│ ├── dev/
│ │ ├── main.tf
│ │ ├── variables.tf
│ │ └── backend.tf
│ ├── staging/
│ │ ├── main.tf
│ │ ├── variables.tf
│ │ └── backend.tf
│ └── prod/
│ ├── main.tf
│ ├── variables.tf
│ └── backend.tf
└── modules/
├── vpc/
├── rds/
└── eks/Setiap environment memiliki own backend configuration:
terraform {
backend "s3" {
bucket = "my-terraform-state"
key = "prod/terraform.tfstate"
region = "us-east-1"
dynamodb_table = "terraform-locks"
encrypt = true
}
}terraform {
backend "s3" {
bucket = "my-terraform-state"
key = "dev/terraform.tfstate"
region = "us-east-1"
dynamodb_table = "terraform-locks"
encrypt = true
}
}Tambahkan safety check untuk prevent accidentally apply prod configuration ke dev:
terraform {
required_version = ">= 1.0"
}
variable "environment" {
type = string
default = "prod"
}
resource "null_resource" "environment_check" {
lifecycle {
precondition {
condition = var.environment == "prod"
error_message = "This configuration is for production only."
}
}
}Jangan pernah commit terraform.tfstate atau terraform.tfstate.backup ke version control. Tambahkan ke .gitignore:
terraform.tfstate
terraform.tfstate.*
.terraform/
.terraform.lock.hclState file contain sensitive data seperti database password, API key, dan private IP. Commit mereka expose informasi ini ke siapa pun dengan repository access.
Terraform state adalah file JSON, dan tempting untuk edit secara langsung. Jangan. Gunakan terraform state command sebagai gantinya:
terraform state rm aws_instance.example
terraform state mv aws_instance.old aws_instance.new
terraform state show aws_instance.exampleManual edit dapat corrupt state file, causing Terraform untuk behave unpredictably.
Backend credential harus dikelola melalui IAM role, bukan shared credential file. Jika Anda menggunakan AWS, gunakan:
Jangan pernah hardcode AWS credential dalam Terraform configuration Anda atau share via Slack.
Ketika Anda clone Terraform repository, run terraform init immediately. Ini download provider dan configure backend. Skip langkah ini berarti Anda bekerja dengan local state, yang mengalahkan purpose dari remote backend.
Sebelum migrate ke new backend dalam production, test dalam non-critical environment terlebih dahulu. State migration biasanya safe, tetapi lebih baik untuk sure.
Untuk team beyond certain size, managed solution seperti Terraform Cloud eliminate backend complexity. Anda mendapat:
Trade-off adalah cost dan less control, tetapi operational simplicity worth untuk most organization.
Bahkan dengan S3 versioning, maintain regular backup:
aws s3 cp s3://my-terraform-state/prod/terraform.tfstate \
s3://my-terraform-backups/prod/terraform.tfstate.$(date +%Y%m%d)Run ini daily via Lambda function atau cron job.
Setup CloudWatch alert untuk state file modification:
resource "aws_cloudwatch_event_rule" "state_changes" {
name = "terraform-state-changes"
description = "Alert on Terraform state file modifications"
event_pattern = jsonencode({
source = ["aws.s3"]
detail-type = ["Object-level API calls via CloudTrail"]
detail = {
bucket = {
name = ["my-terraform-state"]
}
object = {
key = [{
prefix = "prod/terraform.tfstate"
}]
}
eventName = ["PutObject"]
}
})
}Configure lock timeout untuk prevent operation dari hanging indefinitely:
terraform {
backend "s3" {
bucket = "my-terraform-state"
key = "prod/terraform.tfstate"
region = "us-east-1"
dynamodb_table = "terraform-locks"
encrypt = true
skip_credentials_validation = false
skip_metadata_api_check = false
}
}Dalam CI/CD pipeline Anda, set operation timeout:
timeout 30m terraform apply -auto-approveJangan put semua infrastructure Anda dalam satu state file. Pisahkan oleh:
Ini limit blast radius jika sesuatu salah. Mistake dalam dev state file tidak akan affect production.
Untuk personal project atau learning, local state baik-baik saja. Anda adalah satu-satunya user, dan kehilangan state tidak catastrophic.
Jika Anda spinning up infrastructure untuk testing dan tearing down immediately, local state bekerja.
Jika Anda managing infrastructure dalam air-gapped network tanpa internet access, Anda mungkin perlu gunakan local state atau self-hosted backend.
Dalam semua case lain, especially anything touching production, gunakan remote backend.
Terraform state management adalah foundational untuk reliable infrastructure automation. Moving dari local ke remote state dengan S3 dan DynamoDB eliminate most common failure mode: lost state, concurrent modification, dan lack of audit trail.
Takeaway kunci:
Mulai dengan S3 + DynamoDB jika Anda di AWS. Ini battle-tested, cost-effective, dan memberikan Anda full control. Saat team Anda berkembang, evaluate managed solution seperti Terraform Cloud untuk additional collaboration feature.
Waktu yang Anda invest dalam proper state management sekarang prevent infrastructure disaster nanti.