# terraform / aws / s3 / security

Locked Down by Default: S3 Bucket with Security Features

This configuration creates an S3 bucket and layers four security-focused resources on top of it: descriptive tags, a public access block, versioning, and server-side encryption — the baseline most teams expect from any production bucket.

$ terraform apply
bucketakshanmugananthan
regionap-south-1
public accessBlocked
encryptionAES256
4
Resources
1
Bucket
# at a glance

Four Security Controls

Tags
Name · Key
Public Access Block
All 4 flags true
Versioning
Disabled
Encryption
SSE-S3 / AES256
# hcl

The Full Configuration

main.tfTERRAFORM · AWS · S3
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31
# Configure the AWS Provider
provider "aws" {
  region = "ap-south-1"
}

# Create an S3 Bucket
resource "aws_s3_bucket" "akshan" {
  bucket = "akshanmugananthan"

  # Bucket Tags
  tags = {
    Name = "terraform bucket"
    Key  = "trail"
  }
}

# Block Public Access
resource "aws_s3_bucket_public_access_block" "block_public" {
  bucket = aws_s3_bucket.akshan.id

  block_public_acls       = true
  block_public_policy     = true
  ignore_public_acls      = true
  restrict_public_buckets = true
}

# Enable Bucket Versioning
resource "aws_s3_bucket_versioning" "bucket_version" {
  bucket = aws_s3_bucket.akshan.id
  versioning_configuration {
    status = "Disabled"
  }
}

# Enable Server-Side Encryption
resource "aws_s3_bucket_server_side_encryption_configuration" "encrypt" {
  bucket = aws_s3_bucket.akshan.id
  rule {
    apply_server_side_encryption_by_default {
      sse_algorithm = "AES256"
    }
  }
}
# resource by resource

Explanation

provider

region = "ap-south-1"

Configures the AWS provider. Every resource in this file gets created in the Mumbai (ap-south-1) region.

main.tfPROVIDER
1 2 3
provider "aws" {
  region = "ap-south-1"
}
bucket

aws_s3_bucket.akshan

Creates an S3 bucket named akshanmugananthan. The resource name akshan is just a local label — it's how other resources in this file reference the bucket.

main.tfRESOURCE TYPE + NAME
1
resource "aws_s3_bucket" "akshan"
tags

Organizing the Bucket

Tags help you find, filter, and cost-allocate AWS resources later. Neither tag here is required by AWS — they're purely organizational.

TagValue
Nameterraform bucket
Keytrail

aws_s3_bucket_public_access_block.block_public

Prevents the bucket from ever being made publicly accessible, regardless of what an ACL or bucket policy elsewhere might try to grant.

  • block_public_acls

    true — blocks new public ACLs from being applied to the bucket or its objects.

  • block_public_policy

    true — blocks any bucket policy that would grant public access.

  • ignore_public_acls

    true — ignores any public ACLs that already exist on the bucket.

  • restrict_public_buckets

    true — restricts access to the bucket even for policies that would otherwise allow it.

versioning · currently disabled

aws_s3_bucket_versioning.bucket_version

Controls object versioning, which protects against accidental deletion or overwriting by keeping every prior version of an object. This config currently sets it to "Disabled".

main.tfTO ENABLE
1
status = "Enabled"
encryption · SSE-S3

aws_s3_bucket_server_side_encryption_configuration.encrypt

Automatically encrypts every object uploaded to the bucket using AES256 — Amazon S3's own managed server-side encryption. No client-side changes are needed; objects are encrypted at rest by default.

DEFAULT

Applies automatically to every new object — nothing has to opt in at upload time.

ALGORITHM

AES256 is S3-managed (SSE-S3); swap the block for aws:kms to use a KMS key instead.

# linking resources

Resource References

main.tfREFERENCED EVERYWHERE
1
aws_s3_bucket.akshan.id
aws_s3_bucket
↓ resource type
akshan
↓ resource name
.id
↓ attribute
Bucket ID

All three sub-resources — public access block, versioning, and encryption — attach to the bucket the same way: by pointing their bucket argument at this reference.

# running it

Terraform Commands

  1. terraform init — initialize the project and download the AWS provider.
  2. terraform validate — check the configuration for errors.
  3. terraform fmt — format the code to standard style.
  4. terraform plan — preview exactly what will be created.
  5. terraform apply — create the bucket and all four security resources.
  6. terraform destroy — delete everything this configuration manages.
terminalEND TO END
$ terraform init
$ terraform validate
$ terraform fmt
$ terraform plan
$ terraform apply
# when no longer needed
$ terraform destroy