├── .gitignore ├── .travis.yml ├── docs ├── targets.md └── terraform.md ├── Makefile ├── outputs.tf ├── README.yaml ├── main.tf ├── variables.tf └── README.md /.gitignore: -------------------------------------------------------------------------------- 1 | # Compiled files 2 | *.tfstate 3 | *.tfstate.backup 4 | .terraform.tfstate.lock.info 5 | 6 | # Module directory 7 | .terraform/ 8 | .idea 9 | *.iml 10 | 11 | # Build Harness 12 | .build-harness 13 | build-harness/ 14 | -------------------------------------------------------------------------------- /.travis.yml: -------------------------------------------------------------------------------- 1 | addons: 2 | apt: 3 | packages: 4 | - git 5 | - make 6 | - curl 7 | 8 | install: 9 | - make init 10 | 11 | script: 12 | - make terraform/install 13 | - make terraform/get-plugins 14 | - make terraform/get-modules 15 | - make terraform/lint 16 | - make terraform/validate -------------------------------------------------------------------------------- /docs/targets.md: -------------------------------------------------------------------------------- 1 | ## Makefile Targets 2 | ``` 3 | Available targets: 4 | 5 | help Help screen 6 | help/all Display help for all targets 7 | help/short This help short screen 8 | lint Lint terraform code 9 | 10 | ``` 11 | -------------------------------------------------------------------------------- /Makefile: -------------------------------------------------------------------------------- 1 | SHELL := /bin/bash 2 | 3 | # List of targets the `readme` target should call before generating the readme 4 | export README_DEPS ?= docs/targets.md docs/terraform.md 5 | 6 | -include $(shell curl -sSL -o .build-harness "https://git.io/build-harness"; echo .build-harness) 7 | 8 | ## Lint terraform code 9 | lint: 10 | $(SELF) terraform/install terraform/get-modules terraform/get-plugins terraform/lint terraform/validate -------------------------------------------------------------------------------- /outputs.tf: -------------------------------------------------------------------------------- 1 | output "scale_down_policy_arn" { 2 | description = "Autoscaling scale up policy ARN" 3 | value = "${module.autoscaling.scale_down_policy_arn}" 4 | } 5 | 6 | output "scale_up_policy_arn" { 7 | description = "Autoscaling scale up policy ARN" 8 | value = "${module.autoscaling.scale_up_policy_arn}" 9 | } 10 | 11 | output "service_name" { 12 | description = "ECS Service Name" 13 | value = "${module.ecs_alb_service_task.service_name}" 14 | } 15 | 16 | output "task_role_name" { 17 | description = "ECS Task role name" 18 | value = "${module.ecs_alb_service_task.task_role_name}" 19 | } 20 | 21 | output "task_role_arn" { 22 | description = "ECS Task role ARN" 23 | value = "${module.ecs_alb_service_task.task_role_arn}" 24 | } 25 | 26 | output "service_security_group_id" { 27 | description = "Security Group id of the ECS task" 28 | value = "${module.ecs_alb_service_task.service_security_group_id}" 29 | } 30 | 31 | output "badge_url" { 32 | description = "The URL of the build badge when `badge_enabled` is enabled" 33 | value = "${module.ecs_codepipeline.badge_url}" 34 | } 35 | 36 | output "webhook_id" { 37 | description = "The CodePipeline webhook's ARN." 38 | value = "${module.ecs_codepipeline.webhook_id}" 39 | } 40 | 41 | output "webhook_url" { 42 | description = "The CodePipeline webhook's URL. POST events to this endpoint to trigger the target." 43 | value = "${module.ecs_codepipeline.webhook_url}" 44 | sensitive = true 45 | } 46 | -------------------------------------------------------------------------------- /README.yaml: -------------------------------------------------------------------------------- 1 | --- 2 | # 3 | # This is the canonical configuration for the `README.md` 4 | # Run `make readme` to rebuild the `README.md` 5 | # 6 | 7 | # Name of this project 8 | name: terraform-aws-ecs-web-app 9 | 10 | # Logo for this project 11 | #logo: docs/logo.png 12 | 13 | # License of this project 14 | license: "APACHE2" 15 | 16 | # Canonical GitHub repo 17 | github_repo: cloudposse/terraform-aws-ecs-web-app 18 | 19 | # Badges to display 20 | badges: 21 | - name: "Build Status" 22 | image: "https://travis-ci.org/cloudposse/terraform-aws-ecs-web-app.svg?branch=master" 23 | url: "https://travis-ci.org/cloudposse/terraform-aws-ecs-web-app" 24 | - name: "Latest Release" 25 | image: "https://img.shields.io/github/release/cloudposse/terraform-aws-ecs-web-app.svg" 26 | url: "https://github.com/cloudposse/terraform-aws-ecs-web-app/releases/latest" 27 | - name: "Slack Community" 28 | image: "https://slack.cloudposse.com/badge.svg" 29 | url: "https://slack.cloudposse.com" 30 | 31 | related: 32 | - name: "terraform-aws-alb" 33 | description: "Terraform module to provision a standard ALB for HTTP/HTTP traffic" 34 | url: "https://github.com/cloudposse/terraform-aws-alb" 35 | - name: "terraform-aws-alb-ingress" 36 | description: "Terraform module to provision an HTTP style ingress rule based on hostname and path for an ALB" 37 | url: "https://github.com/cloudposse/terraform-aws-alb-ingress" 38 | - name: "terraform-aws-codebuild" 39 | description: "Terraform Module to easily leverage AWS CodeBuild for Continuous Integration" 40 | url: "https://github.com/cloudposse/terraform-aws-codebuild" 41 | - name: "terraform-aws-ecr" 42 | description: "Terraform Module to manage Docker Container Registries on AWS ECR" 43 | url: "https://github.com/cloudposse/terraform-aws-ecr" 44 | - name: "terraform-aws-ecs-alb-service-task" 45 | description: "Terraform module which implements an ECS service which exposes a web service via ALB." 46 | url: "https://github.com/cloudposse/terraform-aws-ecs-alb-service-task" 47 | - name: "terraform-aws-ecs-codepipeline" 48 | description: "Terraform Module for CI/CD with AWS Code Pipeline and Code Build for ECS" 49 | url: "https://github.com/cloudposse/terraform-aws-ecs-codepipeline" 50 | - name: "terraform-aws-ecs-container-definition" 51 | description: "Terraform module to generate well-formed JSON documents that are passed to the aws_ecs_task_definition Terraform resource" 52 | url: "https://github.com/cloudposse/terraform-aws-ecs-container-definition" 53 | - name: "terraform-aws-lb-s3-bucket" 54 | description: "Terraform module to provision an S3 bucket with built in IAM policy to allow AWS Load Balancers to ship access logs." 55 | url: "https://github.com/cloudposse/terraform-aws-lb-s3-bucket" 56 | 57 | 58 | 59 | 60 | # Short description of this project 61 | description: |- 62 | A Terraform module which implements a web app on ECS and supporting AWS resources. 63 | 64 | # How to use this project 65 | usage: |- 66 | ``` 67 | module "default-backend-web-app" { 68 | source = "git::https://github.com/cloudposse/terraform-aws-ecs-web-app.git?ref=tags/0.1.0" 69 | name = "appname" 70 | namespace = "eg" 71 | stage = "testing" 72 | vpc_id = "${module.vpc.vpc_id}" 73 | listener_arns = "${module.alb.listener_arns}" 74 | listener_arns_count = "1" 75 | aws_logs_region = "us-west-2" 76 | ecs_cluster_arn = "${aws_ecs_cluster.default.arn}" 77 | ecs_cluster_name = "${aws_ecs_cluster.default.name}" 78 | ecs_security_group_ids = ["${module.vpc.vpc_default_security_group_id}"] 79 | ecs_private_subnet_ids = ["${module.subnets.private_subnet_ids}"] 80 | alb_ingress_healthcheck_path = "/healthz" 81 | alb_ingress_paths = ["/*"] 82 | codepipeline_enabled = "false" 83 | environment = [ 84 | { 85 | name = "COOKIE" 86 | value = "cookiemonster" 87 | }, 88 | { 89 | name = "PORT" 90 | value = "80" 91 | } 92 | ] 93 | } 94 | ``` 95 | 96 | # Example usage 97 | #examples: |- 98 | # Example goes here... 99 | 100 | # How to get started quickly 101 | #quickstart: |- 102 | # Here's how to get started... 103 | 104 | # Other files to include in this README from the project folder 105 | include: 106 | - "docs/targets.md" 107 | - "docs/terraform.md" 108 | 109 | # Contributors to this project 110 | contributors: 111 | - name: "Erik Osterman" 112 | github: "osterman" 113 | - name: "Igor Rodionov" 114 | github: "goruha" 115 | - name: "Andriy Knysh" 116 | github: "aknysh" 117 | - name: "Sarkis Varozian" 118 | github: "sarkis" 119 | -------------------------------------------------------------------------------- /main.tf: -------------------------------------------------------------------------------- 1 | module "default_label" { 2 | source = "git::https://github.com/cloudposse/terraform-terraform-label.git?ref=tags/0.2.1" 3 | name = "${var.name}" 4 | namespace = "${var.namespace}" 5 | stage = "${var.stage}" 6 | attributes = "${var.attributes}" 7 | } 8 | 9 | module "ecr" { 10 | source = "git::https://github.com/cloudposse/terraform-aws-ecr.git?ref=tags/0.2.9" 11 | name = "${var.name}" 12 | namespace = "${var.namespace}" 13 | stage = "${var.stage}" 14 | attributes = "${compact(concat(var.attributes, list("ecr")))}" 15 | } 16 | 17 | resource "aws_cloudwatch_log_group" "app" { 18 | name = "${module.default_label.id}" 19 | tags = "${module.default_label.tags}" 20 | } 21 | 22 | module "alb_ingress" { 23 | source = "git::https://github.com/cloudposse/terraform-aws-alb-ingress.git?ref=tags/0.3.1" 24 | name = "${var.name}" 25 | namespace = "${var.namespace}" 26 | stage = "${var.stage}" 27 | attributes = "${var.attributes}" 28 | vpc_id = "${var.vpc_id}" 29 | listener_arns = "${var.listener_arns}" 30 | listener_arns_count = "${var.listener_arns_count}" 31 | health_check_path = "${var.alb_ingress_healthcheck_path}" 32 | paths = ["${var.alb_ingress_paths}"] 33 | priority = "${var.alb_ingress_listener_priority}" 34 | hosts = ["${var.alb_ingress_hosts}"] 35 | port = "${var.container_port}" 36 | } 37 | 38 | module "container_definition" { 39 | source = "git::https://github.com/cloudposse/terraform-aws-ecs-container-definition.git?ref=tags/0.3.0" 40 | container_name = "${var.container_name}" 41 | container_image = "${var.container_image}" 42 | container_memory = "${var.container_memory}" 43 | container_memory_reservation = "${var.container_memory_reservation}" 44 | container_cpu = "${var.container_cpu}" 45 | healthcheck = "${var.healthcheck}" 46 | environment = "${var.environment}" 47 | port_mappings = "${var.port_mappings}" 48 | 49 | log_options = { 50 | "awslogs-region" = "${var.aws_logs_region}" 51 | "awslogs-group" = "${aws_cloudwatch_log_group.app.name}" 52 | "awslogs-stream-prefix" = "${var.name}" 53 | } 54 | } 55 | 56 | module "ecs_alb_service_task" { 57 | source = "git::https://github.com/cloudposse/terraform-aws-ecs-alb-service-task.git?ref=tags/0.6.3" 58 | name = "${var.name}" 59 | namespace = "${var.namespace}" 60 | stage = "${var.stage}" 61 | attributes = "${var.attributes}" 62 | alb_target_group_arn = "${module.alb_ingress.target_group_arn}" 63 | container_definition_json = "${module.container_definition.json}" 64 | container_name = "${var.container_name}" 65 | desired_count = "${var.desired_count}" 66 | task_cpu = "${var.container_cpu}" 67 | task_memory = "${var.container_memory}" 68 | ecs_cluster_arn = "${var.ecs_cluster_arn}" 69 | launch_type = "${var.launch_type}" 70 | vpc_id = "${var.vpc_id}" 71 | security_group_ids = ["${var.ecs_security_group_ids}"] 72 | private_subnet_ids = ["${var.ecs_private_subnet_ids}"] 73 | container_port = "${var.container_port}" 74 | } 75 | 76 | module "ecs_codepipeline" { 77 | enabled = "${var.codepipeline_enabled}" 78 | source = "git::https://github.com/Quartz/terraform-aws-ecs-codepipeline.git?ref=tags/0.5.0-patch-20200210" 79 | name = "${var.name}" 80 | namespace = "${var.namespace}" 81 | stage = "${var.stage}" 82 | approve_sns_arn = "${var.codepipeline_approve_sns_arn}" 83 | attributes = "${var.attributes}" 84 | github_oauth_token = "${var.github_oauth_token}" 85 | github_webhook_events = "${var.github_webhook_events}" 86 | repo_owner = "${var.repo_owner}" 87 | repo_name = "${var.repo_name}" 88 | branch = "${var.branch}" 89 | badge_enabled = "${var.badge_enabled}" 90 | build_timeout = "${var.build_timeout}" 91 | buildspec = "${var.buildspec}" 92 | image_repo_name = "${module.ecr.repository_name}" 93 | service_name = "${module.ecs_alb_service_task.service_name}" 94 | staging_service_name = "${var.namespace}-dev-${var.name}" 95 | ecs_cluster_name = "${var.ecs_cluster_name}" 96 | privileged_mode = "true" 97 | poll_source_changes = "${var.poll_source_changes}" 98 | 99 | webhook_enabled = "${var.codepipeline_enabled}" 100 | webhook_target_action = "${var.webhook_target_action}" 101 | webhook_authentication = "${var.webhook_authentication}" 102 | webhook_filter_json_path = "${var.webhook_filter_json_path}" 103 | webhook_filter_match_equals = "${var.webhook_filter_match_equals}" 104 | 105 | environment_variables = [{ 106 | "name" = "CONTAINER_NAME" 107 | 108 | "value" = "${var.container_name}" 109 | }] 110 | } 111 | 112 | module "autoscaling" { 113 | enabled = "${var.autoscaling_enabled}" 114 | source = "git::https://github.com/cloudposse/terraform-aws-ecs-cloudwatch-autoscaling.git?ref=tags/0.1.0" 115 | name = "${var.name}" 116 | namespace = "${var.namespace}" 117 | stage = "${var.stage}" 118 | attributes = "${var.attributes}" 119 | service_name = "${module.ecs_alb_service_task.service_name}" 120 | cluster_name = "${var.ecs_cluster_name}" 121 | min_capacity = "${var.autoscaling_min_capacity}" 122 | max_capacity = "${var.autoscaling_max_capacity}" 123 | scale_down_adjustment = "${var.autoscaling_scale_down_adjustment}" 124 | scale_down_cooldown = "${var.autoscaling_scale_down_cooldown}" 125 | scale_up_adjustment = "${var.autoscaling_scale_up_adjustment}" 126 | scale_up_cooldown = "${var.autoscaling_scale_up_cooldown}" 127 | } 128 | 129 | locals { 130 | cpu_utilization_high_alarm_actions = "${var.autoscaling_enabled == "true" && var.autoscaling_dimension == "cpu" ? module.autoscaling.scale_up_policy_arn : ""}" 131 | cpu_utilization_low_alarm_actions = "${var.autoscaling_enabled == "true" && var.autoscaling_dimension == "cpu" ? module.autoscaling.scale_down_policy_arn : ""}" 132 | memory_utilization_high_alarm_actions = "${var.autoscaling_enabled == "true" && var.autoscaling_dimension == "memory" ? module.autoscaling.scale_up_policy_arn : ""}" 133 | memory_utilization_low_alarm_actions = "${var.autoscaling_enabled == "true" && var.autoscaling_dimension == "memory" ? module.autoscaling.scale_down_policy_arn : ""}" 134 | } 135 | 136 | module "ecs_alarms" { 137 | source = "git::https://github.com/cloudposse/terraform-aws-ecs-cloudwatch-sns-alarms.git?ref=tags/0.4.0" 138 | name = "${var.name}" 139 | namespace = "${var.namespace}" 140 | stage = "${var.stage}" 141 | attributes = "${var.attributes}" 142 | tags = "${var.tags}" 143 | 144 | enabled = "${var.ecs_alarms_enabled}" 145 | cluster_name = "${var.ecs_cluster_name}" 146 | service_name = "${module.ecs_alb_service_task.service_name}" 147 | 148 | cpu_utilization_high_threshold = "${var.ecs_alarms_cpu_utilization_high_threshold}" 149 | cpu_utilization_high_evaluation_periods = "${var.ecs_alarms_cpu_utilization_high_evaluation_periods}" 150 | cpu_utilization_high_period = "${var.ecs_alarms_cpu_utilization_high_period}" 151 | cpu_utilization_high_alarm_actions = "${compact(concat(var.ecs_alarms_cpu_utilization_high_alarm_actions, list(local.cpu_utilization_high_alarm_actions)))}" 152 | cpu_utilization_high_ok_actions = "${var.ecs_alarms_cpu_utilization_high_ok_actions}" 153 | 154 | cpu_utilization_low_threshold = "${var.ecs_alarms_cpu_utilization_low_threshold}" 155 | cpu_utilization_low_evaluation_periods = "${var.ecs_alarms_cpu_utilization_low_evaluation_periods}" 156 | cpu_utilization_low_period = "${var.ecs_alarms_cpu_utilization_low_period}" 157 | cpu_utilization_low_alarm_actions = "${compact(concat(var.ecs_alarms_cpu_utilization_low_alarm_actions, list(local.cpu_utilization_low_alarm_actions)))}" 158 | cpu_utilization_low_ok_actions = "${var.ecs_alarms_cpu_utilization_low_ok_actions}" 159 | 160 | memory_utilization_high_threshold = "${var.ecs_alarms_memory_utilization_high_threshold}" 161 | memory_utilization_high_evaluation_periods = "${var.ecs_alarms_memory_utilization_high_evaluation_periods}" 162 | memory_utilization_high_period = "${var.ecs_alarms_memory_utilization_high_period}" 163 | memory_utilization_high_alarm_actions = "${compact(concat(var.ecs_alarms_memory_utilization_high_alarm_actions, list(local.memory_utilization_high_alarm_actions)))}" 164 | memory_utilization_high_ok_actions = "${var.ecs_alarms_memory_utilization_high_ok_actions}" 165 | 166 | memory_utilization_low_threshold = "${var.ecs_alarms_memory_utilization_low_threshold}" 167 | memory_utilization_low_evaluation_periods = "${var.ecs_alarms_memory_utilization_low_evaluation_periods}" 168 | memory_utilization_low_period = "${var.ecs_alarms_memory_utilization_low_period}" 169 | memory_utilization_low_alarm_actions = "${compact(concat(var.ecs_alarms_memory_utilization_low_alarm_actions, list(local.memory_utilization_low_alarm_actions)))}" 170 | memory_utilization_low_ok_actions = "${var.ecs_alarms_memory_utilization_low_ok_actions}" 171 | } 172 | 173 | module "alb_target_group_alarms" { 174 | enabled = "${var.alb_target_group_alarms_enabled}" 175 | source = "git::https://github.com/cloudposse/terraform-aws-alb-target-group-cloudwatch-sns-alarms.git?ref=tags/0.5.0" 176 | name = "${var.name}" 177 | namespace = "${var.namespace}" 178 | stage = "${var.stage}" 179 | attributes = "${var.attributes}" 180 | alarm_actions = ["${var.alb_target_group_alarms_alarm_actions}"] 181 | ok_actions = ["${var.alb_target_group_alarms_ok_actions}"] 182 | insufficient_data_actions = ["${var.alb_target_group_alarms_insufficient_data_actions}"] 183 | alb_name = "${var.alb_name}" 184 | alb_arn_suffix = "${var.alb_arn_suffix}" 185 | target_group_name = "${module.alb_ingress.target_group_name}" 186 | target_group_arn_suffix = "${module.alb_ingress.target_group_arn_suffix}" 187 | target_3xx_count_threshold = "${var.alb_target_group_alarms_3xx_threshold}" 188 | target_4xx_count_threshold = "${var.alb_target_group_alarms_4xx_threshold}" 189 | target_5xx_count_threshold = "${var.alb_target_group_alarms_5xx_threshold}" 190 | target_response_time_threshold = "${var.alb_target_group_alarms_response_time_threshold}" 191 | period = "${var.alb_target_group_alarms_period}" 192 | evaluation_periods = "${var.alb_target_group_alarms_evaluation_periods}" 193 | } 194 | -------------------------------------------------------------------------------- /docs/terraform.md: -------------------------------------------------------------------------------- 1 | ## Inputs 2 | 3 | | Name | Description | Type | Default | Required | 4 | |------|-------------|:----:|:-----:|:-----:| 5 | | alb_arn_suffix | ARN suffix of the ALB for the Target Group. | string | `` | no | 6 | | alb_ingress_healthcheck_path | The path of the healthcheck which the ALB checks. | string | `/` | no | 7 | | alb_ingress_hosts | Hosts to match in Hosts header, at least one of hosts or paths must be set | list | `` | no | 8 | | alb_ingress_listener_priority | Priority of the listeners, a number between 1 - 50000 (1 is highest priority) | string | `1000` | no | 9 | | alb_ingress_paths | Path pattern to match (a maximum of 1 can be defined), at least one of hosts or paths must be set | list | `` | no | 10 | | alb_name | Name of the ALB for the Target Group. | string | `` | no | 11 | | alb_target_group_alarms_3xx_threshold | The maximum number of 3XX HTTPCodes in a given period for ECS Service. | string | `25` | no | 12 | | alb_target_group_alarms_4xx_threshold | The maximum number of 4XX HTTPCodes in a given period for ECS Service. | string | `25` | no | 13 | | alb_target_group_alarms_5xx_threshold | The maximum number of 5XX HTTPCodes in a given period for ECS Service. | string | `25` | no | 14 | | alb_target_group_alarms_alarm_actions | A list of ARNs (i.e. SNS Topic ARN) to execute when ALB Target Group alarms transition into an ALARM state from any other state. | list | `` | no | 15 | | alb_target_group_alarms_enabled | A boolean to enable/disable CloudWatch Alarms for ALB Target metrics. | string | `false` | no | 16 | | alb_target_group_alarms_evaluation_periods | The number of periods to analyze for ALB CloudWatch Alarms. | string | `1` | no | 17 | | alb_target_group_alarms_insufficient_data_actions | A list of ARNs (i.e. SNS Topic ARN) to execute when ALB Target Group alarms transition into an INSUFFICIENT_DATA state from any other state. | list | `` | no | 18 | | alb_target_group_alarms_ok_actions | A list of ARNs (i.e. SNS Topic ARN) to execute when ALB Target Group alarms transition into an OK state from any other state. | list | `` | no | 19 | | alb_target_group_alarms_period | The period (in seconds) to analyze for ALB CloudWatch Alarms. | string | `300` | no | 20 | | alb_target_group_alarms_response_time_threshold | The maximum ALB Target Group response time. | string | `0.5` | no | 21 | | alb_target_group_arn | Pass target group down to module | string | `` | no | 22 | | attributes | List of attributes to add to label. | list | `` | no | 23 | | autoscaling_dimension | Dimension to autoscale on (valid options: cpu, memory) | string | `memory` | no | 24 | | autoscaling_enabled | A boolean to enable/disable Autoscaling policy for ECS Service. | string | `false` | no | 25 | | autoscaling_max_capacity | Maximum number of running instances of a Service. | string | `2` | no | 26 | | autoscaling_min_capacity | Minimum number of running instances of a Service. | string | `1` | no | 27 | | autoscaling_scale_down_adjustment | Scaling adjustment to make during scale down event. | string | `-1` | no | 28 | | autoscaling_scale_down_cooldown | Period (in seconds) to wait between scale down events. | string | `300` | no | 29 | | autoscaling_scale_up_adjustment | Scaling adjustment to make during scale up event. | string | `1` | no | 30 | | autoscaling_scale_up_cooldown | Period (in seconds) to wait between scale up events. | string | `60` | no | 31 | | aws_logs_region | The region for the AWS Cloudwatch Logs group. | string | - | yes | 32 | | badge_enabled | Generates a publicly-accessible URL for the projects build badge. Available as badge_url attribute when enabled. | string | `false` | no | 33 | | branch | Branch of the GitHub repository, e.g. master | string | `` | no | 34 | | build_timeout | How long in minutes, from 5 to 480 (8 hours), for AWS CodeBuild to wait until timing out any related build that does not get marked as completed. | string | `60` | no | 35 | | buildspec | Declaration to use for building the project. [For more info](http://docs.aws.amazon.com/codebuild/latest/userguide/build-spec-ref.html) | string | `` | no | 36 | | codepipeline_enabled | A boolean to enable/disable AWS Codepipeline and ECR | string | `true` | no | 37 | | container_cpu | The vCPU setting to control cpu limits of container. (If FARGATE launch type is used below, this must be a supported vCPU size from the table here: https://docs.aws.amazon.com/AmazonECS/latest/developerguide/task-cpu-memory-error.html) | string | `256` | no | 38 | | container_image | The default container image to use in container definition. | string | `cloudposse/default-backend` | no | 39 | | container_memory | The amount of RAM to allow container to use in MB. (If FARGATE launch type is used below, this must be a supported Memory size from the table here: https://docs.aws.amazon.com/AmazonECS/latest/developerguide/task-cpu-memory-error.html) | string | `512` | no | 40 | | container_memory_reservation | The amount of RAM (Soft Limit) to allow container to use in MB. This value must be less than container_memory if set. | string | `` | no | 41 | | container_port | The port number on the container bound to assigned host_port. | string | `80` | no | 42 | | delimiter | The delimiter to be used in labels. | string | `-` | no | 43 | | desired_count | The desired number of tasks to start with. Set this to 0 if using DAEMON Service type. (FARGATE does not suppoert DAEMON Service type) | string | `1` | no | 44 | | ecs_alarms_cpu_utilization_high_alarm_actions | A list of ARNs (i.e. SNS Topic ARN) to notify on CPU Utilization High Alarm action. | list | `` | no | 45 | | ecs_alarms_cpu_utilization_high_evaluation_periods | Number of periods to evaluate for the alarm. | string | `1` | no | 46 | | ecs_alarms_cpu_utilization_high_ok_actions | A list of ARNs (i.e. SNS Topic ARN) to notify on CPU Utilization High OK action. | list | `` | no | 47 | | ecs_alarms_cpu_utilization_high_period | Duration in seconds to evaluate for the alarm. | string | `300` | no | 48 | | ecs_alarms_cpu_utilization_high_threshold | The maximum percentage of CPU utilization average. | string | `80` | no | 49 | | ecs_alarms_cpu_utilization_low_alarm_actions | A list of ARNs (i.e. SNS Topic ARN) to notify on CPU Utilization Low Alarm action. | list | `` | no | 50 | | ecs_alarms_cpu_utilization_low_evaluation_periods | Number of periods to evaluate for the alarm. | string | `1` | no | 51 | | ecs_alarms_cpu_utilization_low_ok_actions | A list of ARNs (i.e. SNS Topic ARN) to notify on CPU Utilization Low OK action. | list | `` | no | 52 | | ecs_alarms_cpu_utilization_low_period | Duration in seconds to evaluate for the alarm. | string | `300` | no | 53 | | ecs_alarms_cpu_utilization_low_threshold | The minimum percentage of CPU utilization average. | string | `20` | no | 54 | | ecs_alarms_enabled | A boolean to enable/disable CloudWatch Alarms for ECS Service metrics. | string | `false` | no | 55 | | ecs_alarms_memory_utilization_high_alarm_actions | A list of ARNs (i.e. SNS Topic ARN) to notify on Memory Utilization High Alarm action. | list | `` | no | 56 | | ecs_alarms_memory_utilization_high_evaluation_periods | Number of periods to evaluate for the alarm. | string | `1` | no | 57 | | ecs_alarms_memory_utilization_high_ok_actions | A list of ARNs (i.e. SNS Topic ARN) to notify on Memory Utilization High OK action. | list | `` | no | 58 | | ecs_alarms_memory_utilization_high_period | Duration in seconds to evaluate for the alarm. | string | `300` | no | 59 | | ecs_alarms_memory_utilization_high_threshold | The maximum percentage of Memory utilization average. | string | `80` | no | 60 | | ecs_alarms_memory_utilization_low_alarm_actions | A list of ARNs (i.e. SNS Topic ARN) to notify on Memory Utilization Low Alarm action. | list | `` | no | 61 | | ecs_alarms_memory_utilization_low_evaluation_periods | Number of periods to evaluate for the alarm. | string | `1` | no | 62 | | ecs_alarms_memory_utilization_low_ok_actions | A list of ARNs (i.e. SNS Topic ARN) to notify on Memory Utilization Low OK action. | list | `` | no | 63 | | ecs_alarms_memory_utilization_low_period | Duration in seconds to evaluate for the alarm. | string | `300` | no | 64 | | ecs_alarms_memory_utilization_low_threshold | The minimum percentage of Memory utilization average. | string | `20` | no | 65 | | ecs_cluster_arn | The ECS Cluster ARN where ECS Service will be provisioned. | string | - | yes | 66 | | ecs_cluster_name | The ECS Cluster Name to use in ECS Code Pipeline Deployment step. | string | - | yes | 67 | | ecs_private_subnet_ids | List of Private Subnet IDs to provision ECS Service onto. | list | - | yes | 68 | | ecs_security_group_ids | Additional Security Group IDs to allow into ECS Service. | list | `` | no | 69 | | environment | The environment variables for the task definition. This is a list of maps | list | `` | no | 70 | | github_oauth_token | GitHub Oauth Token with permissions to access private repositories | string | `` | no | 71 | | github_webhook_events | A list of events which should trigger the webhook. See a list of [available events](https://developer.github.com/v3/activity/events/types/). | list | `` | no | 72 | | healthcheck | A map containing command (string), interval (duration in seconds), retries (1-10, number of times to retry before marking container unhealthy, and startPeriod (0-300, optional grace period to wait, in seconds, before failed healthchecks count toward retries) | map | `` | no | 73 | | host_port | The port number to bind container_port to on the host | string | `` | no | 74 | | launch_type | The ECS launch type (valid options: FARGATE or EC2) | string | `FARGATE` | no | 75 | | listener_arns | List of ALB Listener ARNs for the ECS service. | list | - | yes | 76 | | listener_arns_count | Number of elements in list of ALB Listener ARNs for the ECS service. | string | - | yes | 77 | | name | Name (unique identifier for app or service) | string | - | yes | 78 | | namespace | Namespace (e.g. `cp` or `cloudposse`) | string | - | yes | 79 | | poll_source_changes | Periodically check the location of your source content and run the pipeline if changes are detected | string | `false` | no | 80 | | port_mappings | The port mappings to configure for the container. This is a list of maps. Each map should contain "containerPort", "hostPort", and "protocol", where "protocol" is one of "tcp" or "udp". If using containers in a task with the awsvpc or host network mode, the hostPort can either be left blank or set to the same value as the containerPort. | list | `` | no | 81 | | protocol | The protocol used for the port mapping. Options: tcp or udp. | string | `tcp` | no | 82 | | repo_name | GitHub repository name of the application to be built and deployed to ECS. | string | `` | no | 83 | | repo_owner | GitHub Organization or Username. | string | `` | no | 84 | | stage | Stage (e.g. `prod`, `dev`, `staging`) | string | - | yes | 85 | | tags | Map of key-value pairs to use for tags. | map | `` | no | 86 | | vpc_id | The VPC ID where resources are created. | string | - | yes | 87 | | webhook_authentication | The type of authentication to use. One of IP, GITHUB_HMAC, or UNAUTHENTICATED. | string | `GITHUB_HMAC` | no | 88 | | webhook_enabled | Set to false to prevent the module from creating any webhook resources | string | `true` | no | 89 | | webhook_filter_json_path | The JSON path to filter on. | string | `$.ref` | no | 90 | | webhook_filter_match_equals | The value to match on (e.g. refs/heads/{Branch}) | string | `refs/heads/{Branch}` | no | 91 | | webhook_target_action | The name of the action in a pipeline you want to connect to the webhook. The action must be from the source (first) stage of the pipeline. | string | `Source` | no | 92 | 93 | ## Outputs 94 | 95 | | Name | Description | 96 | |------|-------------| 97 | | badge_url | The URL of the build badge when `badge_enabled` is enabled | 98 | | scale_down_policy_arn | Autoscaling scale up policy ARN | 99 | | scale_up_policy_arn | Autoscaling scale up policy ARN | 100 | | service_name | ECS Service Name | 101 | | service_security_group_id | Security Group id of the ECS task | 102 | | task_role_arn | ECS Task role ARN | 103 | | task_role_name | ECS Task role name | 104 | | webhook_id | The CodePipeline webhook's ARN. | 105 | | webhook_url | The CodePipeline webhook's URL. POST events to this endpoint to trigger the target. | 106 | 107 | -------------------------------------------------------------------------------- /variables.tf: -------------------------------------------------------------------------------- 1 | variable "name" { 2 | type = "string" 3 | description = "Name (unique identifier for app or service)" 4 | } 5 | 6 | variable "namespace" { 7 | type = "string" 8 | description = "Namespace (e.g. `cp` or `cloudposse`)" 9 | } 10 | 11 | variable "delimiter" { 12 | type = "string" 13 | description = "The delimiter to be used in labels." 14 | default = "-" 15 | } 16 | 17 | variable "stage" { 18 | type = "string" 19 | description = "Stage (e.g. `prod`, `dev`, `staging`)" 20 | } 21 | 22 | variable "attributes" { 23 | type = "list" 24 | description = "List of attributes to add to label." 25 | default = [] 26 | } 27 | 28 | variable "tags" { 29 | type = "map" 30 | description = "Map of key-value pairs to use for tags." 31 | default = {} 32 | } 33 | 34 | variable "codepipeline_enabled" { 35 | type = "string" 36 | description = "A boolean to enable/disable AWS Codepipeline and ECR" 37 | default = "true" 38 | } 39 | 40 | variable "codepipeline_approve_sns_arn" { 41 | type = "string" 42 | description = "The SNS ARN for Codepipeline approval" 43 | } 44 | 45 | variable "container_name" { 46 | type = "string" 47 | description = "The name of the ECS container." 48 | default = "web" 49 | } 50 | 51 | variable "container_image" { 52 | type = "string" 53 | description = "The default container image to use in container definition." 54 | default = "cloudposse/default-backend" 55 | } 56 | 57 | variable "container_cpu" { 58 | type = "string" 59 | description = "The vCPU setting to control cpu limits of container. (If FARGATE launch type is used below, this must be a supported vCPU size from the table here: https://docs.aws.amazon.com/AmazonECS/latest/developerguide/task-cpu-memory-error.html)" 60 | default = "256" 61 | } 62 | 63 | variable "container_memory" { 64 | type = "string" 65 | description = "The amount of RAM to allow container to use in MB. (If FARGATE launch type is used below, this must be a supported Memory size from the table here: https://docs.aws.amazon.com/AmazonECS/latest/developerguide/task-cpu-memory-error.html)" 66 | default = "512" 67 | } 68 | 69 | variable "container_memory_reservation" { 70 | type = "string" 71 | description = "The amount of RAM (Soft Limit) to allow container to use in MB. This value must be less than container_memory if set." 72 | default = "" 73 | } 74 | 75 | variable "container_port" { 76 | type = "string" 77 | description = "The port number on the container bound to assigned host_port." 78 | default = "80" 79 | } 80 | 81 | variable "port_mappings" { 82 | type = "list" 83 | description = "The port mappings to configure for the container. This is a list of maps. Each map should contain \"containerPort\", \"hostPort\", and \"protocol\", where \"protocol\" is one of \"tcp\" or \"udp\". If using containers in a task with the awsvpc or host network mode, the hostPort can either be left blank or set to the same value as the containerPort." 84 | 85 | default = [{ 86 | "containerPort" = 80 87 | "hostPort" = 80 88 | "protocol" = "tcp" 89 | }] 90 | } 91 | 92 | variable "desired_count" { 93 | type = "string" 94 | description = "The desired number of tasks to start with. Set this to 0 if using DAEMON Service type. (FARGATE does not suppoert DAEMON Service type)" 95 | default = "1" 96 | } 97 | 98 | variable "host_port" { 99 | type = "string" 100 | description = "The port number to bind container_port to on the host" 101 | default = "" 102 | } 103 | 104 | variable "launch_type" { 105 | type = "string" 106 | description = "The ECS launch type (valid options: FARGATE or EC2)" 107 | default = "FARGATE" 108 | } 109 | 110 | variable "environment" { 111 | type = "list" 112 | description = "The environment variables for the task definition. This is a list of maps" 113 | default = [] 114 | } 115 | 116 | variable "protocol" { 117 | type = "string" 118 | description = "The protocol used for the port mapping. Options: tcp or udp." 119 | default = "tcp" 120 | } 121 | 122 | variable "healthcheck" { 123 | type = "map" 124 | description = "A map containing command (string), interval (duration in seconds), retries (1-10, number of times to retry before marking container unhealthy, and startPeriod (0-300, optional grace period to wait, in seconds, before failed healthchecks count toward retries)" 125 | default = {} 126 | } 127 | 128 | variable "alb_target_group_arn" { 129 | type = "string" 130 | description = "Pass target group down to module" 131 | default = "" 132 | } 133 | 134 | variable "alb_target_group_alarms_enabled" { 135 | type = "string" 136 | description = "A boolean to enable/disable CloudWatch Alarms for ALB Target metrics." 137 | default = "false" 138 | } 139 | 140 | variable "alb_target_group_alarms_3xx_threshold" { 141 | type = "string" 142 | description = "The maximum number of 3XX HTTPCodes in a given period for ECS Service." 143 | default = "25" 144 | } 145 | 146 | variable "alb_target_group_alarms_4xx_threshold" { 147 | type = "string" 148 | description = "The maximum number of 4XX HTTPCodes in a given period for ECS Service." 149 | default = "25" 150 | } 151 | 152 | variable "alb_target_group_alarms_5xx_threshold" { 153 | type = "string" 154 | description = "The maximum number of 5XX HTTPCodes in a given period for ECS Service." 155 | default = "25" 156 | } 157 | 158 | variable "alb_target_group_alarms_response_time_threshold" { 159 | type = "string" 160 | description = "The maximum ALB Target Group response time." 161 | default = "0.5" 162 | } 163 | 164 | variable "alb_target_group_alarms_period" { 165 | type = "string" 166 | description = "The period (in seconds) to analyze for ALB CloudWatch Alarms." 167 | default = "300" 168 | } 169 | 170 | variable "alb_target_group_alarms_evaluation_periods" { 171 | type = "string" 172 | description = "The number of periods to analyze for ALB CloudWatch Alarms." 173 | default = "1" 174 | } 175 | 176 | variable "alb_target_group_alarms_alarm_actions" { 177 | type = "list" 178 | description = "A list of ARNs (i.e. SNS Topic ARN) to execute when ALB Target Group alarms transition into an ALARM state from any other state." 179 | default = [] 180 | } 181 | 182 | variable "alb_target_group_alarms_ok_actions" { 183 | type = "list" 184 | description = "A list of ARNs (i.e. SNS Topic ARN) to execute when ALB Target Group alarms transition into an OK state from any other state." 185 | default = [] 186 | } 187 | 188 | variable "alb_target_group_alarms_insufficient_data_actions" { 189 | type = "list" 190 | description = "A list of ARNs (i.e. SNS Topic ARN) to execute when ALB Target Group alarms transition into an INSUFFICIENT_DATA state from any other state." 191 | default = [] 192 | } 193 | 194 | variable "alb_name" { 195 | type = "string" 196 | description = "Name of the ALB for the Target Group." 197 | default = "" 198 | } 199 | 200 | variable "alb_arn_suffix" { 201 | type = "string" 202 | description = "ARN suffix of the ALB for the Target Group." 203 | default = "" 204 | } 205 | 206 | variable "alb_ingress_healthcheck_path" { 207 | type = "string" 208 | description = "The path of the healthcheck which the ALB checks." 209 | default = "/" 210 | } 211 | 212 | variable "alb_ingress_hosts" { 213 | type = "list" 214 | default = [] 215 | description = "Hosts to match in Hosts header, at least one of hosts or paths must be set" 216 | } 217 | 218 | variable "alb_ingress_paths" { 219 | type = "list" 220 | default = [] 221 | description = "Path pattern to match (a maximum of 1 can be defined), at least one of hosts or paths must be set" 222 | } 223 | 224 | variable "alb_ingress_listener_priority" { 225 | type = "string" 226 | default = "1000" 227 | description = "Priority of the listeners, a number between 1 - 50000 (1 is highest priority)" 228 | } 229 | 230 | variable "vpc_id" { 231 | type = "string" 232 | description = "The VPC ID where resources are created." 233 | } 234 | 235 | variable "listener_arns" { 236 | type = "list" 237 | description = "List of ALB Listener ARNs for the ECS service." 238 | } 239 | 240 | variable "listener_arns_count" { 241 | type = "string" 242 | description = "Number of elements in list of ALB Listener ARNs for the ECS service." 243 | } 244 | 245 | variable "aws_logs_region" { 246 | type = "string" 247 | description = "The region for the AWS Cloudwatch Logs group." 248 | } 249 | 250 | variable "ecs_alarms_enabled" { 251 | type = "string" 252 | description = "A boolean to enable/disable CloudWatch Alarms for ECS Service metrics." 253 | default = "false" 254 | } 255 | 256 | variable "ecs_cluster_arn" { 257 | type = "string" 258 | description = "The ECS Cluster ARN where ECS Service will be provisioned." 259 | } 260 | 261 | variable "ecs_cluster_name" { 262 | type = "string" 263 | description = "The ECS Cluster Name to use in ECS Code Pipeline Deployment step." 264 | } 265 | 266 | variable "ecs_alarms_cpu_utilization_high_threshold" { 267 | type = "string" 268 | description = "The maximum percentage of CPU utilization average." 269 | default = "80" 270 | } 271 | 272 | variable "ecs_alarms_cpu_utilization_high_evaluation_periods" { 273 | type = "string" 274 | description = "Number of periods to evaluate for the alarm." 275 | default = "1" 276 | } 277 | 278 | variable "ecs_alarms_cpu_utilization_high_period" { 279 | type = "string" 280 | description = "Duration in seconds to evaluate for the alarm." 281 | default = "300" 282 | } 283 | 284 | variable "ecs_alarms_cpu_utilization_high_alarm_actions" { 285 | type = "list" 286 | description = "A list of ARNs (i.e. SNS Topic ARN) to notify on CPU Utilization High Alarm action." 287 | default = [] 288 | } 289 | 290 | variable "ecs_alarms_cpu_utilization_high_ok_actions" { 291 | type = "list" 292 | description = "A list of ARNs (i.e. SNS Topic ARN) to notify on CPU Utilization High OK action." 293 | default = [] 294 | } 295 | 296 | variable "ecs_alarms_cpu_utilization_low_threshold" { 297 | type = "string" 298 | description = "The minimum percentage of CPU utilization average." 299 | default = "20" 300 | } 301 | 302 | variable "ecs_alarms_cpu_utilization_low_evaluation_periods" { 303 | type = "string" 304 | description = "Number of periods to evaluate for the alarm." 305 | default = "1" 306 | } 307 | 308 | variable "ecs_alarms_cpu_utilization_low_period" { 309 | type = "string" 310 | description = "Duration in seconds to evaluate for the alarm." 311 | default = "300" 312 | } 313 | 314 | variable "ecs_alarms_cpu_utilization_low_alarm_actions" { 315 | type = "list" 316 | description = "A list of ARNs (i.e. SNS Topic ARN) to notify on CPU Utilization Low Alarm action." 317 | default = [] 318 | } 319 | 320 | variable "ecs_alarms_cpu_utilization_low_ok_actions" { 321 | type = "list" 322 | description = "A list of ARNs (i.e. SNS Topic ARN) to notify on CPU Utilization Low OK action." 323 | default = [] 324 | } 325 | 326 | variable "ecs_alarms_memory_utilization_high_threshold" { 327 | type = "string" 328 | description = "The maximum percentage of Memory utilization average." 329 | default = "80" 330 | } 331 | 332 | variable "ecs_alarms_memory_utilization_high_evaluation_periods" { 333 | type = "string" 334 | description = "Number of periods to evaluate for the alarm." 335 | default = "1" 336 | } 337 | 338 | variable "ecs_alarms_memory_utilization_high_period" { 339 | type = "string" 340 | description = "Duration in seconds to evaluate for the alarm." 341 | default = "300" 342 | } 343 | 344 | variable "ecs_alarms_memory_utilization_high_alarm_actions" { 345 | type = "list" 346 | description = "A list of ARNs (i.e. SNS Topic ARN) to notify on Memory Utilization High Alarm action." 347 | default = [] 348 | } 349 | 350 | variable "ecs_alarms_memory_utilization_high_ok_actions" { 351 | type = "list" 352 | description = "A list of ARNs (i.e. SNS Topic ARN) to notify on Memory Utilization High OK action." 353 | default = [] 354 | } 355 | 356 | variable "ecs_alarms_memory_utilization_low_threshold" { 357 | type = "string" 358 | description = "The minimum percentage of Memory utilization average." 359 | default = "20" 360 | } 361 | 362 | variable "ecs_alarms_memory_utilization_low_evaluation_periods" { 363 | type = "string" 364 | description = "Number of periods to evaluate for the alarm." 365 | default = "1" 366 | } 367 | 368 | variable "ecs_alarms_memory_utilization_low_period" { 369 | type = "string" 370 | description = "Duration in seconds to evaluate for the alarm." 371 | default = "300" 372 | } 373 | 374 | variable "ecs_alarms_memory_utilization_low_alarm_actions" { 375 | type = "list" 376 | description = "A list of ARNs (i.e. SNS Topic ARN) to notify on Memory Utilization Low Alarm action." 377 | default = [] 378 | } 379 | 380 | variable "ecs_alarms_memory_utilization_low_ok_actions" { 381 | type = "list" 382 | description = "A list of ARNs (i.e. SNS Topic ARN) to notify on Memory Utilization Low OK action." 383 | default = [] 384 | } 385 | 386 | variable "ecs_security_group_ids" { 387 | type = "list" 388 | description = "Additional Security Group IDs to allow into ECS Service." 389 | default = [] 390 | } 391 | 392 | variable "ecs_private_subnet_ids" { 393 | type = "list" 394 | description = "List of Private Subnet IDs to provision ECS Service onto." 395 | } 396 | 397 | variable "github_oauth_token" { 398 | type = "string" 399 | description = "GitHub Oauth Token with permissions to access private repositories" 400 | default = "" 401 | } 402 | 403 | variable "github_webhook_events" { 404 | description = "A list of events which should trigger the webhook. See a list of [available events](https://developer.github.com/v3/activity/events/types/)." 405 | default = ["push"] 406 | } 407 | 408 | variable "repo_owner" { 409 | type = "string" 410 | description = "GitHub Organization or Username." 411 | default = "" 412 | } 413 | 414 | variable "repo_name" { 415 | type = "string" 416 | description = "GitHub repository name of the application to be built and deployed to ECS." 417 | default = "" 418 | } 419 | 420 | variable "branch" { 421 | type = "string" 422 | description = "Branch of the GitHub repository, e.g. master" 423 | default = "" 424 | } 425 | 426 | variable "badge_enabled" { 427 | type = "string" 428 | default = "false" 429 | description = "Generates a publicly-accessible URL for the projects build badge. Available as badge_url attribute when enabled." 430 | } 431 | 432 | variable "build_timeout" { 433 | type = "string" 434 | default = "60" 435 | description = "How long in minutes, from 5 to 480 (8 hours), for AWS CodeBuild to wait until timing out any related build that does not get marked as completed." 436 | } 437 | 438 | variable "buildspec" { 439 | default = "" 440 | description = "Declaration to use for building the project. [For more info](http://docs.aws.amazon.com/codebuild/latest/userguide/build-spec-ref.html)" 441 | } 442 | 443 | variable "autoscaling_enabled" { 444 | type = "string" 445 | description = "A boolean to enable/disable Autoscaling policy for ECS Service." 446 | default = "false" 447 | } 448 | 449 | variable "autoscaling_dimension" { 450 | type = "string" 451 | description = "Dimension to autoscale on (valid options: cpu, memory)" 452 | default = "memory" 453 | } 454 | 455 | variable "autoscaling_min_capacity" { 456 | type = "string" 457 | description = "Minimum number of running instances of a Service." 458 | default = "1" 459 | } 460 | 461 | variable "autoscaling_max_capacity" { 462 | type = "string" 463 | description = "Maximum number of running instances of a Service." 464 | default = "2" 465 | } 466 | 467 | variable "autoscaling_scale_up_adjustment" { 468 | type = "string" 469 | description = "Scaling adjustment to make during scale up event." 470 | default = "1" 471 | } 472 | 473 | variable "autoscaling_scale_up_cooldown" { 474 | type = "string" 475 | description = "Period (in seconds) to wait between scale up events." 476 | default = "60" 477 | } 478 | 479 | variable "autoscaling_scale_down_adjustment" { 480 | type = "string" 481 | description = "Scaling adjustment to make during scale down event." 482 | default = "-1" 483 | } 484 | 485 | variable "autoscaling_scale_down_cooldown" { 486 | type = "string" 487 | description = "Period (in seconds) to wait between scale down events." 488 | default = "300" 489 | } 490 | 491 | # https://www.terraform.io/docs/configuration/variables.html 492 | # It is recommended you avoid using boolean values and use explicit strings 493 | variable "poll_source_changes" { 494 | type = "string" 495 | default = "false" 496 | description = "Periodically check the location of your source content and run the pipeline if changes are detected" 497 | } 498 | 499 | variable "webhook_enabled" { 500 | description = "Set to false to prevent the module from creating any webhook resources" 501 | default = "true" 502 | } 503 | 504 | variable "webhook_target_action" { 505 | description = "The name of the action in a pipeline you want to connect to the webhook. The action must be from the source (first) stage of the pipeline." 506 | default = "Source" 507 | } 508 | 509 | variable "webhook_authentication" { 510 | description = "The type of authentication to use. One of IP, GITHUB_HMAC, or UNAUTHENTICATED." 511 | default = "GITHUB_HMAC" 512 | } 513 | 514 | variable "webhook_filter_json_path" { 515 | description = "The JSON path to filter on." 516 | default = "$.ref" 517 | } 518 | 519 | variable "webhook_filter_match_equals" { 520 | description = "The value to match on (e.g. refs/heads/{Branch})" 521 | default = "refs/heads/{Branch}" 522 | } 523 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | 2 | [![README Header][readme_header_img]][readme_header_link] 3 | 4 | [![Cloud Posse][logo]](https://cpco.io/homepage) 5 | 6 | # terraform-aws-ecs-web-app [![Build Status](https://travis-ci.org/cloudposse/terraform-aws-ecs-web-app.svg?branch=master)](https://travis-ci.org/cloudposse/terraform-aws-ecs-web-app) [![Latest Release](https://img.shields.io/github/release/cloudposse/terraform-aws-ecs-web-app.svg)](https://github.com/cloudposse/terraform-aws-ecs-web-app/releases/latest) [![Slack Community](https://slack.cloudposse.com/badge.svg)](https://slack.cloudposse.com) 7 | 8 | 9 | A Terraform module which implements a web app on ECS and supporting AWS resources. 10 | 11 | 12 | --- 13 | 14 | This project is part of our comprehensive ["SweetOps"](https://cpco.io/sweetops) approach towards DevOps. 15 | [][share_email] 16 | [][share_googleplus] 17 | [][share_facebook] 18 | [][share_reddit] 19 | [][share_linkedin] 20 | [][share_twitter] 21 | 22 | 23 | [![Terraform Open Source Modules](https://docs.cloudposse.com/images/terraform-open-source-modules.svg)][terraform_modules] 24 | 25 | 26 | 27 | It's 100% Open Source and licensed under the [APACHE2](LICENSE). 28 | 29 | 30 | 31 | 32 | 33 | 34 | 35 | We literally have [*hundreds of terraform modules*][terraform_modules] that are Open Source and well-maintained. Check them out! 36 | 37 | 38 | 39 | 40 | 41 | 42 | 43 | ## Usage 44 | 45 | ``` 46 | module "default-backend-web-app" { 47 | source = "git::https://github.com/cloudposse/terraform-aws-ecs-web-app.git?ref=tags/0.1.0" 48 | name = "appname" 49 | namespace = "eg" 50 | stage = "testing" 51 | vpc_id = "${module.vpc.vpc_id}" 52 | listener_arns = "${module.alb.listener_arns}" 53 | listener_arns_count = "1" 54 | aws_logs_region = "us-west-2" 55 | ecs_cluster_arn = "${aws_ecs_cluster.default.arn}" 56 | ecs_cluster_name = "${aws_ecs_cluster.default.name}" 57 | ecs_security_group_ids = ["${module.vpc.vpc_default_security_group_id}"] 58 | ecs_private_subnet_ids = ["${module.subnets.private_subnet_ids}"] 59 | alb_ingress_healthcheck_path = "/healthz" 60 | alb_ingress_paths = ["/*"] 61 | codepipeline_enabled = "false" 62 | environment = [ 63 | { 64 | name = "COOKIE" 65 | value = "cookiemonster" 66 | }, 67 | { 68 | name = "PORT" 69 | value = "80" 70 | } 71 | ] 72 | } 73 | ``` 74 | 75 | 76 | 77 | 78 | 79 | 80 | ## Makefile Targets 81 | ``` 82 | Available targets: 83 | 84 | help Help screen 85 | help/all Display help for all targets 86 | help/short This help short screen 87 | lint Lint terraform code 88 | 89 | ``` 90 | ## Inputs 91 | 92 | | Name | Description | Type | Default | Required | 93 | |------|-------------|:----:|:-----:|:-----:| 94 | | alb_arn_suffix | ARN suffix of the ALB for the Target Group. | string | `` | no | 95 | | alb_ingress_healthcheck_path | The path of the healthcheck which the ALB checks. | string | `/` | no | 96 | | alb_ingress_hosts | Hosts to match in Hosts header, at least one of hosts or paths must be set | list | `` | no | 97 | | alb_ingress_listener_priority | Priority of the listeners, a number between 1 - 50000 (1 is highest priority) | string | `1000` | no | 98 | | alb_ingress_paths | Path pattern to match (a maximum of 1 can be defined), at least one of hosts or paths must be set | list | `` | no | 99 | | alb_name | Name of the ALB for the Target Group. | string | `` | no | 100 | | alb_target_group_alarms_3xx_threshold | The maximum number of 3XX HTTPCodes in a given period for ECS Service. | string | `25` | no | 101 | | alb_target_group_alarms_4xx_threshold | The maximum number of 4XX HTTPCodes in a given period for ECS Service. | string | `25` | no | 102 | | alb_target_group_alarms_5xx_threshold | The maximum number of 5XX HTTPCodes in a given period for ECS Service. | string | `25` | no | 103 | | alb_target_group_alarms_alarm_actions | A list of ARNs (i.e. SNS Topic ARN) to execute when ALB Target Group alarms transition into an ALARM state from any other state. | list | `` | no | 104 | | alb_target_group_alarms_enabled | A boolean to enable/disable CloudWatch Alarms for ALB Target metrics. | string | `false` | no | 105 | | alb_target_group_alarms_evaluation_periods | The number of periods to analyze for ALB CloudWatch Alarms. | string | `1` | no | 106 | | alb_target_group_alarms_insufficient_data_actions | A list of ARNs (i.e. SNS Topic ARN) to execute when ALB Target Group alarms transition into an INSUFFICIENT_DATA state from any other state. | list | `` | no | 107 | | alb_target_group_alarms_ok_actions | A list of ARNs (i.e. SNS Topic ARN) to execute when ALB Target Group alarms transition into an OK state from any other state. | list | `` | no | 108 | | alb_target_group_alarms_period | The period (in seconds) to analyze for ALB CloudWatch Alarms. | string | `300` | no | 109 | | alb_target_group_alarms_response_time_threshold | The maximum ALB Target Group response time. | string | `0.5` | no | 110 | | alb_target_group_arn | Pass target group down to module | string | `` | no | 111 | | attributes | List of attributes to add to label. | list | `` | no | 112 | | autoscaling_dimension | Dimension to autoscale on (valid options: cpu, memory) | string | `memory` | no | 113 | | autoscaling_enabled | A boolean to enable/disable Autoscaling policy for ECS Service. | string | `false` | no | 114 | | autoscaling_max_capacity | Maximum number of running instances of a Service. | string | `2` | no | 115 | | autoscaling_min_capacity | Minimum number of running instances of a Service. | string | `1` | no | 116 | | autoscaling_scale_down_adjustment | Scaling adjustment to make during scale down event. | string | `-1` | no | 117 | | autoscaling_scale_down_cooldown | Period (in seconds) to wait between scale down events. | string | `300` | no | 118 | | autoscaling_scale_up_adjustment | Scaling adjustment to make during scale up event. | string | `1` | no | 119 | | autoscaling_scale_up_cooldown | Period (in seconds) to wait between scale up events. | string | `60` | no | 120 | | aws_logs_region | The region for the AWS Cloudwatch Logs group. | string | - | yes | 121 | | badge_enabled | Generates a publicly-accessible URL for the projects build badge. Available as badge_url attribute when enabled. | string | `false` | no | 122 | | branch | Branch of the GitHub repository, e.g. master | string | `` | no | 123 | | build_timeout | How long in minutes, from 5 to 480 (8 hours), for AWS CodeBuild to wait until timing out any related build that does not get marked as completed. | string | `60` | no | 124 | | buildspec | Declaration to use for building the project. [For more info](http://docs.aws.amazon.com/codebuild/latest/userguide/build-spec-ref.html) | string | `` | no | 125 | | codepipeline_enabled | A boolean to enable/disable AWS Codepipeline and ECR | string | `true` | no | 126 | | container_cpu | The vCPU setting to control cpu limits of container. (If FARGATE launch type is used below, this must be a supported vCPU size from the table here: https://docs.aws.amazon.com/AmazonECS/latest/developerguide/task-cpu-memory-error.html) | string | `256` | no | 127 | | container_image | The default container image to use in container definition. | string | `cloudposse/default-backend` | no | 128 | | container_memory | The amount of RAM to allow container to use in MB. (If FARGATE launch type is used below, this must be a supported Memory size from the table here: https://docs.aws.amazon.com/AmazonECS/latest/developerguide/task-cpu-memory-error.html) | string | `512` | no | 129 | | container_memory_reservation | The amount of RAM (Soft Limit) to allow container to use in MB. This value must be less than container_memory if set. | string | `` | no | 130 | | container_port | The port number on the container bound to assigned host_port. | string | `80` | no | 131 | | delimiter | The delimiter to be used in labels. | string | `-` | no | 132 | | desired_count | The desired number of tasks to start with. Set this to 0 if using DAEMON Service type. (FARGATE does not suppoert DAEMON Service type) | string | `1` | no | 133 | | ecs_alarms_cpu_utilization_high_alarm_actions | A list of ARNs (i.e. SNS Topic ARN) to notify on CPU Utilization High Alarm action. | list | `` | no | 134 | | ecs_alarms_cpu_utilization_high_evaluation_periods | Number of periods to evaluate for the alarm. | string | `1` | no | 135 | | ecs_alarms_cpu_utilization_high_ok_actions | A list of ARNs (i.e. SNS Topic ARN) to notify on CPU Utilization High OK action. | list | `` | no | 136 | | ecs_alarms_cpu_utilization_high_period | Duration in seconds to evaluate for the alarm. | string | `300` | no | 137 | | ecs_alarms_cpu_utilization_high_threshold | The maximum percentage of CPU utilization average. | string | `80` | no | 138 | | ecs_alarms_cpu_utilization_low_alarm_actions | A list of ARNs (i.e. SNS Topic ARN) to notify on CPU Utilization Low Alarm action. | list | `` | no | 139 | | ecs_alarms_cpu_utilization_low_evaluation_periods | Number of periods to evaluate for the alarm. | string | `1` | no | 140 | | ecs_alarms_cpu_utilization_low_ok_actions | A list of ARNs (i.e. SNS Topic ARN) to notify on CPU Utilization Low OK action. | list | `` | no | 141 | | ecs_alarms_cpu_utilization_low_period | Duration in seconds to evaluate for the alarm. | string | `300` | no | 142 | | ecs_alarms_cpu_utilization_low_threshold | The minimum percentage of CPU utilization average. | string | `20` | no | 143 | | ecs_alarms_enabled | A boolean to enable/disable CloudWatch Alarms for ECS Service metrics. | string | `false` | no | 144 | | ecs_alarms_memory_utilization_high_alarm_actions | A list of ARNs (i.e. SNS Topic ARN) to notify on Memory Utilization High Alarm action. | list | `` | no | 145 | | ecs_alarms_memory_utilization_high_evaluation_periods | Number of periods to evaluate for the alarm. | string | `1` | no | 146 | | ecs_alarms_memory_utilization_high_ok_actions | A list of ARNs (i.e. SNS Topic ARN) to notify on Memory Utilization High OK action. | list | `` | no | 147 | | ecs_alarms_memory_utilization_high_period | Duration in seconds to evaluate for the alarm. | string | `300` | no | 148 | | ecs_alarms_memory_utilization_high_threshold | The maximum percentage of Memory utilization average. | string | `80` | no | 149 | | ecs_alarms_memory_utilization_low_alarm_actions | A list of ARNs (i.e. SNS Topic ARN) to notify on Memory Utilization Low Alarm action. | list | `` | no | 150 | | ecs_alarms_memory_utilization_low_evaluation_periods | Number of periods to evaluate for the alarm. | string | `1` | no | 151 | | ecs_alarms_memory_utilization_low_ok_actions | A list of ARNs (i.e. SNS Topic ARN) to notify on Memory Utilization Low OK action. | list | `` | no | 152 | | ecs_alarms_memory_utilization_low_period | Duration in seconds to evaluate for the alarm. | string | `300` | no | 153 | | ecs_alarms_memory_utilization_low_threshold | The minimum percentage of Memory utilization average. | string | `20` | no | 154 | | ecs_cluster_arn | The ECS Cluster ARN where ECS Service will be provisioned. | string | - | yes | 155 | | ecs_cluster_name | The ECS Cluster Name to use in ECS Code Pipeline Deployment step. | string | - | yes | 156 | | ecs_private_subnet_ids | List of Private Subnet IDs to provision ECS Service onto. | list | - | yes | 157 | | ecs_security_group_ids | Additional Security Group IDs to allow into ECS Service. | list | `` | no | 158 | | environment | The environment variables for the task definition. This is a list of maps | list | `` | no | 159 | | github_oauth_token | GitHub Oauth Token with permissions to access private repositories | string | `` | no | 160 | | github_webhook_events | A list of events which should trigger the webhook. See a list of [available events](https://developer.github.com/v3/activity/events/types/). | list | `` | no | 161 | | healthcheck | A map containing command (string), interval (duration in seconds), retries (1-10, number of times to retry before marking container unhealthy, and startPeriod (0-300, optional grace period to wait, in seconds, before failed healthchecks count toward retries) | map | `` | no | 162 | | host_port | The port number to bind container_port to on the host | string | `` | no | 163 | | launch_type | The ECS launch type (valid options: FARGATE or EC2) | string | `FARGATE` | no | 164 | | listener_arns | List of ALB Listener ARNs for the ECS service. | list | - | yes | 165 | | listener_arns_count | Number of elements in list of ALB Listener ARNs for the ECS service. | string | - | yes | 166 | | name | Name (unique identifier for app or service) | string | - | yes | 167 | | namespace | Namespace (e.g. `cp` or `cloudposse`) | string | - | yes | 168 | | poll_source_changes | Periodically check the location of your source content and run the pipeline if changes are detected | string | `false` | no | 169 | | port_mappings | The port mappings to configure for the container. This is a list of maps. Each map should contain "containerPort", "hostPort", and "protocol", where "protocol" is one of "tcp" or "udp". If using containers in a task with the awsvpc or host network mode, the hostPort can either be left blank or set to the same value as the containerPort. | list | `` | no | 170 | | protocol | The protocol used for the port mapping. Options: tcp or udp. | string | `tcp` | no | 171 | | repo_name | GitHub repository name of the application to be built and deployed to ECS. | string | `` | no | 172 | | repo_owner | GitHub Organization or Username. | string | `` | no | 173 | | stage | Stage (e.g. `prod`, `dev`, `staging`) | string | - | yes | 174 | | tags | Map of key-value pairs to use for tags. | map | `` | no | 175 | | vpc_id | The VPC ID where resources are created. | string | - | yes | 176 | | webhook_authentication | The type of authentication to use. One of IP, GITHUB_HMAC, or UNAUTHENTICATED. | string | `GITHUB_HMAC` | no | 177 | | webhook_enabled | Set to false to prevent the module from creating any webhook resources | string | `true` | no | 178 | | webhook_filter_json_path | The JSON path to filter on. | string | `$.ref` | no | 179 | | webhook_filter_match_equals | The value to match on (e.g. refs/heads/{Branch}) | string | `refs/heads/{Branch}` | no | 180 | | webhook_target_action | The name of the action in a pipeline you want to connect to the webhook. The action must be from the source (first) stage of the pipeline. | string | `Source` | no | 181 | 182 | ## Outputs 183 | 184 | | Name | Description | 185 | |------|-------------| 186 | | badge_url | The URL of the build badge when `badge_enabled` is enabled | 187 | | scale_down_policy_arn | Autoscaling scale up policy ARN | 188 | | scale_up_policy_arn | Autoscaling scale up policy ARN | 189 | | service_name | ECS Service Name | 190 | | service_security_group_id | Security Group id of the ECS task | 191 | | task_role_arn | ECS Task role ARN | 192 | | task_role_name | ECS Task role name | 193 | | webhook_id | The CodePipeline webhook's ARN. | 194 | | webhook_url | The CodePipeline webhook's URL. POST events to this endpoint to trigger the target. | 195 | 196 | 197 | 198 | 199 | ## Share the Love 200 | 201 | Like this project? Please give it a ★ on [our GitHub](https://github.com/cloudposse/terraform-aws-ecs-web-app)! (it helps us **a lot**) 202 | 203 | Are you using this project or any of our other projects? Consider [leaving a testimonial][testimonial]. =) 204 | 205 | 206 | ## Related Projects 207 | 208 | Check out these related projects. 209 | 210 | - [terraform-aws-alb](https://github.com/cloudposse/terraform-aws-alb) - Terraform module to provision a standard ALB for HTTP/HTTP traffic 211 | - [terraform-aws-alb-ingress](https://github.com/cloudposse/terraform-aws-alb-ingress) - Terraform module to provision an HTTP style ingress rule based on hostname and path for an ALB 212 | - [terraform-aws-codebuild](https://github.com/cloudposse/terraform-aws-codebuild) - Terraform Module to easily leverage AWS CodeBuild for Continuous Integration 213 | - [terraform-aws-ecr](https://github.com/cloudposse/terraform-aws-ecr) - Terraform Module to manage Docker Container Registries on AWS ECR 214 | - [terraform-aws-ecs-alb-service-task](https://github.com/cloudposse/terraform-aws-ecs-alb-service-task) - Terraform module which implements an ECS service which exposes a web service via ALB. 215 | - [terraform-aws-ecs-codepipeline](https://github.com/cloudposse/terraform-aws-ecs-codepipeline) - Terraform Module for CI/CD with AWS Code Pipeline and Code Build for ECS 216 | - [terraform-aws-ecs-container-definition](https://github.com/cloudposse/terraform-aws-ecs-container-definition) - Terraform module to generate well-formed JSON documents that are passed to the aws_ecs_task_definition Terraform resource 217 | - [terraform-aws-lb-s3-bucket](https://github.com/cloudposse/terraform-aws-lb-s3-bucket) - Terraform module to provision an S3 bucket with built in IAM policy to allow AWS Load Balancers to ship access logs. 218 | 219 | 220 | 221 | ## Help 222 | 223 | **Got a question?** 224 | 225 | File a GitHub [issue](https://github.com/cloudposse/terraform-aws-ecs-web-app/issues), send us an [email][email] or join our [Slack Community][slack]. 226 | 227 | [![README Commercial Support][readme_commercial_support_img]][readme_commercial_support_link] 228 | 229 | ## Commercial Support 230 | 231 | Work directly with our team of DevOps experts via email, slack, and video conferencing. 232 | 233 | We provide [*commercial support*][commercial_support] for all of our [Open Source][github] projects. As a *Dedicated Support* customer, you have access to our team of subject matter experts at a fraction of the cost of a full-time engineer. 234 | 235 | [![E-Mail](https://img.shields.io/badge/email-hello@cloudposse.com-blue.svg)][email] 236 | 237 | - **Questions.** We'll use a Shared Slack channel between your team and ours. 238 | - **Troubleshooting.** We'll help you triage why things aren't working. 239 | - **Code Reviews.** We'll review your Pull Requests and provide constructive feedback. 240 | - **Bug Fixes.** We'll rapidly work to fix any bugs in our projects. 241 | - **Build New Terraform Modules.** We'll [develop original modules][module_development] to provision infrastructure. 242 | - **Cloud Architecture.** We'll assist with your cloud strategy and design. 243 | - **Implementation.** We'll provide hands-on support to implement our reference architectures. 244 | 245 | 246 | 247 | ## Terraform Module Development 248 | 249 | Are you interested in custom Terraform module development? Submit your inquiry using [our form][module_development] today and we'll get back to you ASAP. 250 | 251 | 252 | ## Slack Community 253 | 254 | Join our [Open Source Community][slack] on Slack. It's **FREE** for everyone! Our "SweetOps" community is where you get to talk with others who share a similar vision for how to rollout and manage infrastructure. This is the best place to talk shop, ask questions, solicit feedback, and work together as a community to build totally *sweet* infrastructure. 255 | 256 | ## Newsletter 257 | 258 | Signup for [our newsletter][newsletter] that covers everything on our technology radar. Receive updates on what we're up to on GitHub as well as awesome new projects we discover. 259 | 260 | ## Contributing 261 | 262 | ### Bug Reports & Feature Requests 263 | 264 | Please use the [issue tracker](https://github.com/cloudposse/terraform-aws-ecs-web-app/issues) to report any bugs or file feature requests. 265 | 266 | ### Developing 267 | 268 | If you are interested in being a contributor and want to get involved in developing this project or [help out](https://cpco.io/help-out) with our other projects, we would love to hear from you! Shoot us an [email][email]. 269 | 270 | In general, PRs are welcome. We follow the typical "fork-and-pull" Git workflow. 271 | 272 | 1. **Fork** the repo on GitHub 273 | 2. **Clone** the project to your own machine 274 | 3. **Commit** changes to your own branch 275 | 4. **Push** your work back up to your fork 276 | 5. Submit a **Pull Request** so that we can review your changes 277 | 278 | **NOTE:** Be sure to merge the latest changes from "upstream" before making a pull request! 279 | 280 | 281 | ## Copyright 282 | 283 | Copyright © 2017-2019 [Cloud Posse, LLC](https://cpco.io/copyright) 284 | 285 | 286 | 287 | ## License 288 | 289 | [![License](https://img.shields.io/badge/License-Apache%202.0-blue.svg)](https://opensource.org/licenses/Apache-2.0) 290 | 291 | See [LICENSE](LICENSE) for full details. 292 | 293 | Licensed to the Apache Software Foundation (ASF) under one 294 | or more contributor license agreements. See the NOTICE file 295 | distributed with this work for additional information 296 | regarding copyright ownership. The ASF licenses this file 297 | to you under the Apache License, Version 2.0 (the 298 | "License"); you may not use this file except in compliance 299 | with the License. You may obtain a copy of the License at 300 | 301 | https://www.apache.org/licenses/LICENSE-2.0 302 | 303 | Unless required by applicable law or agreed to in writing, 304 | software distributed under the License is distributed on an 305 | "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 306 | KIND, either express or implied. See the License for the 307 | specific language governing permissions and limitations 308 | under the License. 309 | 310 | 311 | 312 | 313 | 314 | 315 | 316 | 317 | 318 | ## Trademarks 319 | 320 | All other trademarks referenced herein are the property of their respective owners. 321 | 322 | ## About 323 | 324 | This project is maintained and funded by [Cloud Posse, LLC][website]. Like it? Please let us know by [leaving a testimonial][testimonial]! 325 | 326 | [![Cloud Posse][logo]][website] 327 | 328 | We're a [DevOps Professional Services][hire] company based in Los Angeles, CA. We ❤️ [Open Source Software][we_love_open_source]. 329 | 330 | We offer [paid support][commercial_support] on all of our projects. 331 | 332 | Check out [our other projects][github], [follow us on twitter][twitter], [apply for a job][jobs], or [hire us][hire] to help with your cloud strategy and implementation. 333 | 334 | 335 | 336 | ### Contributors 337 | 338 | | [![Erik Osterman][osterman_avatar]][osterman_homepage]
[Erik Osterman][osterman_homepage] | [![Igor Rodionov][goruha_avatar]][goruha_homepage]
[Igor Rodionov][goruha_homepage] | [![Andriy Knysh][aknysh_avatar]][aknysh_homepage]
[Andriy Knysh][aknysh_homepage] | [![Sarkis Varozian][sarkis_avatar]][sarkis_homepage]
[Sarkis Varozian][sarkis_homepage] | 339 | |---|---|---|---| 340 | 341 | [osterman_homepage]: https://github.com/osterman 342 | [osterman_avatar]: https://github.com/osterman.png?size=150 343 | [goruha_homepage]: https://github.com/goruha 344 | [goruha_avatar]: https://github.com/goruha.png?size=150 345 | [aknysh_homepage]: https://github.com/aknysh 346 | [aknysh_avatar]: https://github.com/aknysh.png?size=150 347 | [sarkis_homepage]: https://github.com/sarkis 348 | [sarkis_avatar]: https://github.com/sarkis.png?size=150 349 | 350 | 351 | 352 | [![README Footer][readme_footer_img]][readme_footer_link] 353 | [![Beacon][beacon]][website] 354 | 355 | [logo]: https://cloudposse.com/logo-300x69.svg 356 | [docs]: https://cpco.io/docs 357 | [website]: https://cpco.io/homepage 358 | [github]: https://cpco.io/github 359 | [jobs]: https://cpco.io/jobs 360 | [hire]: https://cpco.io/hire 361 | [slack]: https://cpco.io/slack 362 | [linkedin]: https://cpco.io/linkedin 363 | [twitter]: https://cpco.io/twitter 364 | [testimonial]: https://cpco.io/leave-testimonial 365 | [newsletter]: https://cpco.io/newsletter 366 | [email]: https://cpco.io/email 367 | [commercial_support]: https://cpco.io/commercial-support 368 | [we_love_open_source]: https://cpco.io/we-love-open-source 369 | [module_development]: https://cpco.io/module-development 370 | [terraform_modules]: https://cpco.io/terraform-modules 371 | [readme_header_img]: https://cloudposse.com/readme/header/img?repo=cloudposse/terraform-aws-ecs-web-app 372 | [readme_header_link]: https://cloudposse.com/readme/header/link?repo=cloudposse/terraform-aws-ecs-web-app 373 | [readme_footer_img]: https://cloudposse.com/readme/footer/img?repo=cloudposse/terraform-aws-ecs-web-app 374 | [readme_footer_link]: https://cloudposse.com/readme/footer/link?repo=cloudposse/terraform-aws-ecs-web-app 375 | [readme_commercial_support_img]: https://cloudposse.com/readme/commercial-support/img?repo=cloudposse/terraform-aws-ecs-web-app 376 | [readme_commercial_support_link]: https://cloudposse.com/readme/commercial-support/link?repo=cloudposse/terraform-aws-ecs-web-app 377 | [share_twitter]: https://twitter.com/intent/tweet/?text=terraform-aws-ecs-web-app&url=https://github.com/cloudposse/terraform-aws-ecs-web-app 378 | [share_linkedin]: https://www.linkedin.com/shareArticle?mini=true&title=terraform-aws-ecs-web-app&url=https://github.com/cloudposse/terraform-aws-ecs-web-app 379 | [share_reddit]: https://reddit.com/submit/?url=https://github.com/cloudposse/terraform-aws-ecs-web-app 380 | [share_facebook]: https://facebook.com/sharer/sharer.php?u=https://github.com/cloudposse/terraform-aws-ecs-web-app 381 | [share_googleplus]: https://plus.google.com/share?url=https://github.com/cloudposse/terraform-aws-ecs-web-app 382 | [share_email]: mailto:?subject=terraform-aws-ecs-web-app&body=https://github.com/cloudposse/terraform-aws-ecs-web-app 383 | [beacon]: https://ga-beacon.cloudposse.com/UA-76589703-4/cloudposse/terraform-aws-ecs-web-app?pixel&cs=github&cm=readme&an=terraform-aws-ecs-web-app 384 | --------------------------------------------------------------------------------