/terraform-aws-s3-static-website-cloudfront-ssl-r53

Module built to provision a static website on an S3 bucket. Modules have been broken down into redistributable pieces.

Primary LanguageHCLApache License 2.0Apache-2.0

S3_Static_Website

This module allows the creation of a static S3 website, with Cloudfront as the CDN, with automatic ACM and Route53 configurations.

Motivation

I have seen modules that do exactly what I'm doing here a few times, but they always seem to be in a flat structure (nothing wrong with that!). I thought it may provide a little more value if we could separate the provisioning of ACM / Route53 into it's own module, since it accomplishes one goal. For instance, I may want to provision a cert and dns records, but not necessarily for a static S3 bucket. The s3_static_website module still isn't fully standalone yet, but hopefully with a few minor tweaks I can get that working as well :)

Optionally you can also use this module to:

  • Deploy a redirect bucket to redirect www to non-www.
  • Enable KMS encryption on your S3 log buckets.
  • Enable KMS key rotation.
  • Enable access logging for buckets and Cloudfront.
  • Apply IaM policies so only Cloudfront can access your buckets directly.

This module can be ran stand-alone with just a .tfvars file / env variables; or you may couple it with other modules for CI/CD, etc.

If you notice any issues with the module, please raise an issue! I'm here to help! I plan on using my modules in a personal project, so I want them to be top-notch!

Please Note While I have tried to follow the best security practices out-of-the-box, there is still some recommended setup. Please consider creating a WAF (Web application Firewall) in front of your cloudfront distribution. It is highly recommended that you use one, especially in a production environment. That said, WAF's are very situation-specific, so I cannot guess how your setup should behave. WAF Terraform Docs. Last but not least, you may also want to add a Lambda@Edge function between cloudfront and your bucket, to add an extra layer of security headers.

Running the module

To run the module, simply plug in the values below into a .tfvars file or export the equivalent env variables, and run the below commands

  • terraform init
  • terraform plan (make sure you like what you see on the console before going to the next step!)
  • terraform apply

Example

terraform {
  required_providers {
    aws = {
      source  = "hashicorp/aws"
      version = "3.59.0"
    }
  }
}

module "aws_static_website" {
  source = "https://github.com/millbj92/terraform-aws-s3-static-website-cloudfront-ssl-r53"
  //common
  domain_name = var.domain_name

  //s3_static_site specific
  use_default_domain     = var.use_default_domain
  logging                = var.logging
  use_bucket_encryption  = var.use_bucket_encryption
  enable_key_rotation    = var.enable_key_rotation
  tags                   = var.tags
  deploy_redirect_bucket = var.deploy_redirect_bucket
  force_destroy          = var.force_destroy

  //acm & Route53 specific
  subject_alternative_name_prefixes = var.subject_alternative_name_prefixes
  hosted_zone                       = var.hosted_zone
  acm_certificate_domain            = var.acm_certificate_domain
  preprod_env_prefixes              = var.preprod_env_prefixes
}

 

Documentation

Requirements

No requirements.

Providers

Name Version
aws 3.59.0

Modules

Name Source Version
acm ./acm n/a
s3_static_website ./s3_static_website n/a

Resources

Name Type
aws_route53_record.website_cdn_root_record resource
aws_route53_zone.main data source

Inputs

Name Description Type
domain_name Domain name. Must be unique, and already registered. string
hosted_zone The root domain of your website. No subdomains. (example.com) string
acm_certificate_domain Domain of the ACM certificate string
aws_certificate_arn ARN for SSL certificate. Only needed for custom domain names. string
deploy_redirect_bucket Set this to true to deploy a bucket what will redirect from www to non-www bool
enable_key_rotation Set this to true in order to enable key rotation. Only works if use_bucket_encryption is true. Recommend setting to true so you don't get locked out of your buckets! bool
force_destroy This value will force-delete your buckets with files sill inside. You have been warned. Do not use in Prod. bool
log_cookies Log cookies in cloudfront. Only works in logging is true. bool
logging Use logging for resources. Will create an extra bucket. bool
preprod_env_prefixes Use these to register subdomains in Route53. Leave this empty if you don't want subdomains. list(string)
price_class CloudFront distribution price class string
subject_alternative_name_prefixes Alternative names for the domain. Wildcards mau be used. (*.example.com, etc) list(string)
tags Tags to set on the resources. map(string)
use_bucket_encryption Set this to true to encrypt your buckets with a KMS key. bool
use_default_domain Use CloudFront website address without Route53 and ACM certificate string

Outputs

Name Description
acm_certificate_arn The ARN of the SSL certificate returned from ACM.
cloudfront_dist_id Cloudfront Distribution ID for this site.
cloudfront_domain_name The domain name used by your cloudfront distribution. If you are using the 'default_domain' variable, you would use this.
log_bucket_KMS_key_arn The arn of the created KMS key for the logging bucket. Used for encrypting/decrypting the bucket.
s3_domain_name The domain name of your S3 bucket. For reference only. Either use the Cloudfront Distrobution, or 'website_address' output.
s3_log_bucket_arn The arn of the created s3 logging bucket.
s3_log_bucket_name The name of the created s3 logging bucket
website_address If not using the 'default_domain' variable, this will return your Route53 domain name.
website_bucket_arn The arn of the created s3 website bucket.
website_bucket_name The name of the created s3 website bucket.