Skip to main content
Service Catalog Version 0.111.7Last updated in version 0.110.3

Application Load Balancer

View SourceRelease Notes

Overview

This service contains code to deploy Application Load Balancer on AWS.

ALB architectureALB architecture

Features

  • Deploy public or internal Application Load Balancers
  • Configure DNS in Route 53
  • Configure TLS in AWS Certificate Manager (ACM)
  • Send access logs into S3
  • Manage access with security groups or CIDR blocks

Learn

note

This repo is a part of the Gruntwork Service Catalog, a collection of reusable, battle-tested, production ready infrastructure code. If you’ve never used the Service Catalog before, make sure to read How to use the Gruntwork Service Catalog!

  • Gruntwork Documentation on ALBs: Background information from Gruntwork about ALBs including what it is, differences from other ELB flavors, and when you should use ALBs.

  • ALB Documentation: Amazon’s docs for ALB that cover core concepts such as listeners, target groups, autoscaling, TLS and migrations.

Deploy

Non-production deployment (quick start for learning)

If you just want to try this repo out for experimenting and learning, check out the following resources:

  • examples/for-learning-and-testing folder: The examples/for-learning-and-testing folder contains standalone sample code optimized for learning, experimenting, and testing (but not direct production usage).

Production deployment

If you want to deploy this repo in production, check out the following resources:

Sample Usage

main.tf

# ------------------------------------------------------------------------------------------------------
# DEPLOY GRUNTWORK'S ALB MODULE
# ------------------------------------------------------------------------------------------------------

module "alb" {

source = "git::git@github.com:gruntwork-io/terraform-aws-service-catalog.git//modules/networking/alb?ref=v0.111.7"

# ----------------------------------------------------------------------------------------------------
# REQUIRED VARIABLES
# ----------------------------------------------------------------------------------------------------

# The name of the ALB.
alb_name = <string>

# If the ALB should only accept traffic from within the VPC, set this to true.
# If it should accept traffic from the public Internet, set it to false.
is_internal_alb = <bool>

# After this number of days, log files should be transitioned from S3 to
# Glacier. Enter 0 to never archive log data.
num_days_after_which_archive_log_data = <number>

# After this number of days, log files should be deleted from S3. Enter 0 to
# never delete log data.
num_days_after_which_delete_log_data = <number>

# ID of the VPC where the ALB will be deployed
vpc_id = <string>

# The ids of the subnets that the ALB can use to source its IP
vpc_subnet_ids = <list(string)>

# ----------------------------------------------------------------------------------------------------
# OPTIONAL VARIABLES
# ----------------------------------------------------------------------------------------------------

# The name to use for the S3 bucket where the ALB access logs will be stored.
# If you set this to null, a name will be generated automatically based on
# var.alb_name.
access_logs_s3_bucket_name = null

# When looking up the ACM certs passed in via
# https_listener_ports_and_acm_ssl_certs, only match certs with the given
# statuses. Valid values are PENDING_VALIDATION, ISSUED, INACTIVE, EXPIRED,
# VALIDATION_TIMED_OUT, REVOKED and FAILED.
acm_cert_statuses = ["ISSUED"]

# When looking up the ACM certs passed in via
# https_listener_ports_and_acm_ssl_certs, only match certs of the given types.
# Valid values are AMAZON_ISSUED and IMPORTED.
acm_cert_types = ["AMAZON_ISSUED","IMPORTED"]

# List of additional SSL certs (non-ACM and ACM) to bind to the given listener
# port. Note that this must not overlap with the certificates defined in
# var.https_listener_ports_and_ssl_certs and
# var.https_listener_ports_and_acm_ssl_certs. The keys are the listener ports.
additional_ssl_certs_for_ports = {}

# Set to true to enable all outbound traffic on this ALB. If set to false, the
# ALB will allow no outbound traffic by default. This will make the ALB
# unusuable, so some other code must then update the ALB Security Group to
# enable outbound access!
allow_all_outbound = true

# The CIDR-formatted IP Address range from which this ALB will allow incoming
# requests. If var.is_internal_alb is false, use the default value. If
# var.is_internal_alb is true, consider setting this to the VPC's CIDR Block,
# or something even more restrictive.
allow_inbound_from_cidr_blocks = []

# The list of IDs of security groups that should have access to the ALB
allow_inbound_from_security_group_ids = []

# Set to true to create a Route 53 DNS A record for this ALB?
create_route53_entry = false

# Prefix to use for access logs to create a sub-folder in S3 Bucket name where
# ALB logs should be stored. Only used if
# var.enable_custom_alb_access_logs_s3_prefix is true.
custom_alb_access_logs_s3_prefix = null

# A map of custom tags to apply to the ALB and its Security Group. The key is
# the tag name and the value is the tag value.
custom_tags = {}

# Define the default action if a request to the load balancer does not match
# any of your listener rules. Currently only 'fixed-response' and 'redirect'
# are supported.
# https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/lb_listener#default_action
default_action = {"fixed-response":{"content_type":"text/plain","message_body":null,"status_code":404}}

# If a request to the load balancer does not match any of your listener rules,
# the default action will return a fixed response with this body.
default_action_body = null

# If a request to the load balancer does not match any of your listener rules,
# the default action will return a fixed response with this status code.
default_action_status_code = 404

# The list of domain names for the DNS A record to add for the ALB (e.g.
# alb.foo.com). Only used if var.create_route53_entry is true.
domain_names = []

# If true, the ALB will drop invalid headers. Elastic Load Balancing requires
# that message header names contain only alphanumeric characters and hyphens.
drop_invalid_header_fields = false

# Set to true to use the value of alb_access_logs_s3_prefix for access logs
# prefix. If false, the alb_name will be used. This is useful if you wish to
# disable the S3 prefix. Only used if var.enable_alb_access_logs is true.
enable_custom_alb_access_logs_s3_prefix = false

# Enable deletion protection on the ALB instance. If this is enabled, the load
# balancer cannot be deleted prior to disabling
enable_deletion_protection = false

# A boolean that indicates whether the access logs bucket should be destroyed,
# even if there are files in it, when you run Terraform destroy. Unless you
# are using this bucket only for test purposes, you'll want to leave this
# variable set to false.
force_destroy = false

# The ID of the hosted zone for the DNS A record to add for the ALB. Only used
# if var.create_route53_entry is true.
hosted_zone_id = null

# A list of ports for which an HTTP Listener should be created on the ALB.
# Tip: When you define Listener Rules for these Listeners, be sure that, for
# each Listener, at least one Listener Rule uses the '*' path to ensure that
# every possible request path for that Listener is handled by a Listener Rule.
# Otherwise some requests won't route to any Target Group.
http_listener_ports = []

# A list of the ports for which an HTTPS Listener should be created on the
# ALB. Each item in the list should be a map with the keys 'port', the port
# number to listen on, and 'tls_domain_name', the domain name of an SSL/TLS
# certificate issued by the Amazon Certificate Manager (ACM) to associate with
# the Listener to be created. If your certificate isn't issued by ACM, specify
# var.https_listener_ports_and_ssl_certs instead. Tip: When you define
# Listener Rules for these Listeners, be sure that, for each Listener, at
# least one Listener Rule uses the '*' path to ensure that every possible
# request path for that Listener is handled by a Listener Rule. Otherwise some
# requests won't route to any Target Group.
https_listener_ports_and_acm_ssl_certs = []

# A list of the ports for which an HTTPS Listener should be created on the
# ALB. Each item in the list should be a map with the keys 'port', the port
# number to listen on, and 'tls_arn', the Amazon Resource Name (ARN) of the
# SSL/TLS certificate to associate with the Listener to be created. If your
# certificate is issued by the Amazon Certificate Manager (ACM), specify
# var.https_listener_ports_and_acm_ssl_certs instead. Tip: When you define
# Listener Rules for these Listeners, be sure that, for each Listener, at
# least one Listener Rule uses the '*' path to ensure that every possible
# request path for that Listener is handled by a Listener Rule. Otherwise some
# requests won't route to any Target Group.
https_listener_ports_and_ssl_certs = []

# The time in seconds that the client TCP connection to the ALB is allowed to
# be idle before the ALB closes the TCP connection.
idle_timeout = 60

# The type of IP addresses used by the subnets for your load balancer. The
# possible values are ipv4 and dualstack.
ip_address_type = null

# If true, create a new S3 bucket for access logs with the name in
# var.access_logs_s3_bucket_name. If false, assume the S3 bucket for access
# logs with the name in var.access_logs_s3_bucket_name already exists, and
# don't create a new one. Note that if you set this to false, it's up to you
# to ensure that the S3 bucket has a bucket policy that grants Elastic Load
# Balancing permission to write the access logs to your bucket.
should_create_access_logs_bucket = true

# The AWS predefined TLS/SSL policy for the ALB. A List of policies can be
# found here:
# https://docs.aws.amazon.com/elasticloadbalancing/latest/application/create-https-listener.html#describe-ssl-policies.
# AWS recommends ELBSecurityPolicy-2016-08 policy for general use but this
# policy includes TLSv1.0 which is rapidly being phased out.
# ELBSecurityPolicy-TLS-1-1-2017-01 is the next policy up that doesn't include
# TLSv1.0.
ssl_policy = "ELBSecurityPolicy-2016-08"

}


Reference

Required

alb_namestringrequired

The name of the ALB.

is_internal_albboolrequired

If the ALB should only accept traffic from within the VPC, set this to true. If it should accept traffic from the public Internet, set it to false.

After this number of days, log files should be transitioned from S3 to Glacier. Enter 0 to never archive log data.

After this number of days, log files should be deleted from S3. Enter 0 to never delete log data.

vpc_idstringrequired

ID of the VPC where the ALB will be deployed

vpc_subnet_idslist(string)required

The ids of the subnets that the ALB can use to source its IP

Optional

The name to use for the S3 bucket where the ALB access logs will be stored. If you set this to null, a name will be generated automatically based on alb_name.

null
acm_cert_statuseslist(string)optional

When looking up the ACM certs passed in via https_listener_ports_and_acm_ssl_certs, only match certs with the given statuses. Valid values are PENDING_VALIDATION, ISSUED, INACTIVE, EXPIRED, VALIDATION_TIMED_OUT, REVOKED and FAILED.

[ "ISSUED" ]
acm_cert_typeslist(string)optional

When looking up the ACM certs passed in via https_listener_ports_and_acm_ssl_certs, only match certs of the given types. Valid values are AMAZON_ISSUED and IMPORTED.

[
"AMAZON_ISSUED",
"IMPORTED"
]
additional_ssl_certs_for_portsmap(list(…))optional

List of additional SSL certs (non-ACM and ACM) to bind to the given listener port. Note that this must not overlap with the certificates defined in https_listener_ports_and_ssl_certs and https_listener_ports_and_acm_ssl_certs. The keys are the listener ports.

map(list(object({
# Exactly one of the following must be set, with the other set to null.
# The domain name to use when looking up the ACM cert to associate.
tls_domain_name = string
# The ARN of the TLS cert to associate with the listener.
tls_arn = string
})))
{}
allow_all_outboundbooloptional

Set to true to enable all outbound traffic on this ALB. If set to false, the ALB will allow no outbound traffic by default. This will make the ALB unusuable, so some other code must then update the ALB Security Group to enable outbound access!

true
allow_inbound_from_cidr_blockslist(string)optional

The CIDR-formatted IP Address range from which this ALB will allow incoming requests. If is_internal_alb is false, use the default value. If is_internal_alb is true, consider setting this to the VPC's CIDR Block, or something even more restrictive.

[]

The list of IDs of security groups that should have access to the ALB

[]

Set to true to create a Route 53 DNS A record for this ALB?

false

Prefix to use for access logs to create a sub-folder in S3 Bucket name where ALB logs should be stored. Only used if enable_custom_alb_access_logs_s3_prefix is true.

null
custom_tagsmap(string)optional

A map of custom tags to apply to the ALB and its Security Group. The key is the tag name and the value is the tag value.

{}
default_actionmap(any)optional

Define the default action if a request to the load balancer does not match any of your listener rules. Currently only 'fixed-response' and 'redirect' are supported. https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/lb_listener#default_action

Any types represent complex values of variable type. For details, please consult `variables.tf` in the source repo.
{
fixed-response = {
content_type = "text/plain",
message_body = null,
status_code = 404
}
}
default_action_bodystringoptional

If a request to the load balancer does not match any of your listener rules, the default action will return a fixed response with this body.

null

If a request to the load balancer does not match any of your listener rules, the default action will return a fixed response with this status code.

404
domain_nameslist(string)optional

The list of domain names for the DNS A record to add for the ALB (e.g. alb.foo.com). Only used if create_route53_entry is true.

[]

If true, the ALB will drop invalid headers. Elastic Load Balancing requires that message header names contain only alphanumeric characters and hyphens.

false

Set to true to use the value of alb_access_logs_s3_prefix for access logs prefix. If false, the alb_name will be used. This is useful if you wish to disable the S3 prefix. Only used if enable_alb_access_logs is true.

false

Enable deletion protection on the ALB instance. If this is enabled, the load balancer cannot be deleted prior to disabling

false
force_destroybooloptional

A boolean that indicates whether the access logs bucket should be destroyed, even if there are files in it, when you run Terraform destroy. Unless you are using this bucket only for test purposes, you'll want to leave this variable set to false.

false
hosted_zone_idstringoptional

The ID of the hosted zone for the DNS A record to add for the ALB. Only used if create_route53_entry is true.

null
http_listener_portslist(string)optional

A list of ports for which an HTTP Listener should be created on the ALB. Tip: When you define Listener Rules for these Listeners, be sure that, for each Listener, at least one Listener Rule uses the '*' path to ensure that every possible request path for that Listener is handled by a Listener Rule. Otherwise some requests won't route to any Target Group.

[]

A list of the ports for which an HTTPS Listener should be created on the ALB. Each item in the list should be a map with the keys 'port', the port number to listen on, and 'tls_domain_name', the domain name of an SSL/TLS certificate issued by the Amazon Certificate Manager (ACM) to associate with the Listener to be created. If your certificate isn't issued by ACM, specify https_listener_ports_and_ssl_certs instead. Tip: When you define Listener Rules for these Listeners, be sure that, for each Listener, at least one Listener Rule uses the '*' path to ensure that every possible request path for that Listener is handled by a Listener Rule. Otherwise some requests won't route to any Target Group.

list(object({
port = number
tls_domain_name = string
}))
[]
Example
   default = [
{
port = 443
tls_domain_name = "foo.your-company.com"
}
]

https_listener_ports_and_ssl_certslist(object(…))optional

A list of the ports for which an HTTPS Listener should be created on the ALB. Each item in the list should be a map with the keys 'port', the port number to listen on, and 'tls_arn', the Amazon Resource Name (ARN) of the SSL/TLS certificate to associate with the Listener to be created. If your certificate is issued by the Amazon Certificate Manager (ACM), specify https_listener_ports_and_acm_ssl_certs instead. Tip: When you define Listener Rules for these Listeners, be sure that, for each Listener, at least one Listener Rule uses the '*' path to ensure that every possible request path for that Listener is handled by a Listener Rule. Otherwise some requests won't route to any Target Group.

list(object({
port = number
tls_arn = string
}))
[]
Example
   default = [
{
port = 443
tls_arn = "arn:aws:iam::123456789012:server-certificate/ProdServerCert"
}
]

idle_timeoutnumberoptional

The time in seconds that the client TCP connection to the ALB is allowed to be idle before the ALB closes the TCP connection.

60
ip_address_typestringoptional

The type of IP addresses used by the subnets for your load balancer. The possible values are ipv4 and dualstack.

null

If true, create a new S3 bucket for access logs with the name in access_logs_s3_bucket_name. If false, assume the S3 bucket for access logs with the name in access_logs_s3_bucket_name already exists, and don't create a new one. Note that if you set this to false, it's up to you to ensure that the S3 bucket has a bucket policy that grants Elastic Load Balancing permission to write the access logs to your bucket.

true
ssl_policystringoptional

The AWS predefined TLS/SSL policy for the ALB. A List of policies can be found here: https://docs.aws.amazon.com/elasticloadbalancing/latest/application/create-https-listener.html#describe-ssl-policies. AWS recommends ELBSecurityPolicy-2016-08 policy for general use but this policy includes TLSv1.0 which is rapidly being phased out. ELBSecurityPolicy-TLS-1-1-2017-01 is the next policy up that doesn't include TLSv1.0.

"ELBSecurityPolicy-2016-08"