DEV Community

Bartłomiej Danek
Bartłomiej Danek

Posted on • Originally published at bard.sh

Terraform S3 backend with state locking

S3 backend with state locking

S3 stores the state file, DynamoDB handles locking - prevents two apply runs from corrupting state simultaneously.

setup

terraform {
  backend "s3" {
    bucket         = "my-tf-state"
    key            = "prod/terraform.tfstate"
    region         = "us-east-1"
    encrypt        = true
    dynamodb_table = "terraform-locks"
  }
}
Enter fullscreen mode Exit fullscreen mode

create the S3 bucket and DynamoDB table

resource "aws_s3_bucket" "tf_state" {
  bucket = "my-tf-state"
}

resource "aws_s3_bucket_versioning" "tf_state" {
  bucket = aws_s3_bucket.tf_state.id
  versioning_configuration {
    status = "Enabled"
  }
}

resource "aws_s3_bucket_server_side_encryption_configuration" "tf_state" {
  bucket = aws_s3_bucket.tf_state.id
  rule {
    apply_server_side_encryption_by_default {
      sse_algorithm = "AES256"
    }
  }
}

resource "aws_dynamodb_table" "tf_locks" {
  name         = "terraform-locks"
  billing_mode = "PAY_PER_REQUEST"
  hash_key     = "LockID"

  attribute {
    name = "LockID"
    type = "S"
  }
}
Enter fullscreen mode Exit fullscreen mode

state locking in action

$ terraform apply
Acquiring state lock. This may take a few moments...

# if another process holds the lock:
Error: Error acquiring the state lock
Lock Info:
  ID:        abc-123
  Path:      prod/terraform.tfstate
  Operation: OperationTypeApply
  Who:       alice@machine
  Created:   2024-10-14 12:00:00
Enter fullscreen mode Exit fullscreen mode

force-unlock (use carefully)

terraform force-unlock <lock-id>
Enter fullscreen mode Exit fullscreen mode

per-environment keys

# dev
backend "s3" {
  key = "dev/terraform.tfstate"
}

# prod
backend "s3" {
  key = "prod/terraform.tfstate"
}
Enter fullscreen mode Exit fullscreen mode

Originally published at https://bard.sh/posts/terraform_s3_backend/

Top comments (0)