-
-
Notifications
You must be signed in to change notification settings - Fork 87
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Merge pull request #556 from kayac/example-with-terraform
Add example with terraform
- Loading branch information
Showing
14 changed files
with
606 additions
and
0 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,2 @@ | ||
terraform.tfstate* | ||
.terraform* |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,85 @@ | ||
## An example of deployments by ecspresso and Terraform | ||
|
||
This example shows how to deploy an ECS service by ecspresso and Terraform. | ||
|
||
### Prerequisites | ||
|
||
- [Terraform](https://www.terraform.io/) >= v1.4.0 | ||
- [ecspresso](https://github.com/kayac/ecspresso) >= v2.0.0 | ||
|
||
#### Environment variables | ||
|
||
- `AWS_REGION` for AWS region. (e.g. `ap-northeast-1`) | ||
- `AWS_ACCESS_KEY_ID` and `AWS_SECRET_ACCESS_KEY`, or `AWS_PROFILE` for AWS credentials. | ||
- `AWS_SDK_LOAD_CONFIG=true` may be required if you use `AWS_PROFILE` and `~/.aws/config`. | ||
|
||
### Usage | ||
|
||
Terraform creates AWS resources (VPC, Subnets, ALB, IAM roles, ECS cluster, etc.) for ECS service working with ALB. And ecspresso deploys the service into the ECS cluster. | ||
|
||
```console | ||
$ terraform init | ||
$ terraform apply | ||
$ ecspresso verify | ||
$ ecspresso deploy | ||
``` | ||
|
||
After completing the deployment, you can access the service via ALB. | ||
|
||
```console | ||
$ curl -s "http://$(terraform output -raw alb_dns_name)/" | ||
``` | ||
|
||
Note: This example contains availability zone named a, b, and d. If your AWS account does not have some of them, you can change the resources for them from [vpc.tf](./vpc.tf), [alb.tf](./alb.tf) and [ecs-service-def.jsonnet](./ecs-service-def.jsonnet). | ||
|
||
### Usage with AWS CodeDeploy | ||
|
||
At first, you must delete an ECS service that having "ECS" deployment controller. | ||
|
||
```console | ||
$ ecspresso delete --force --terminate | ||
``` | ||
|
||
Note: After the ECS service is deleted, wait a few minutes until the ECS service is completely removed. While `ecspresso status` reports `DRAINING`, you cannot create a new ECS service with the same name. After `ecspresso status` reports `is INACTIVE`, you can continue to the next step. | ||
|
||
Edit `ecs-service-def.jsonnet`. Remove `deploymentCircuitBreaker` block and change `deployment_controller` to `CODE_DEPLOY`. | ||
|
||
```diff | ||
{ | ||
deploymentConfiguration: { | ||
- deploymentCircuitBreaker: { | ||
- enable: false, | ||
- rollback: false, | ||
- }, | ||
maximumPercent: 200, | ||
minimumHealthyPercent: 100, | ||
}, | ||
deploymentController: { | ||
- type: 'ECS', | ||
+ type: 'CODE_DEPLOY', | ||
}, | ||
``` | ||
|
||
Then deploy the service again. | ||
|
||
```console | ||
$ ecspresso deploy | ||
``` | ||
|
||
After completing the deployment, you have to create a CodeDeploy application and deployment group. | ||
Uncomment [codedeploy.tf](./codedeploy.tf) and run `terraform apply` again. | ||
|
||
Now you can deploy the service by ecspresso using CodeDeploy! | ||
|
||
```console | ||
$ ecspresso deploy | ||
``` | ||
|
||
### Cleanup | ||
|
||
You must delete the ECS service and tasks first. And then, you can delete the resources created by Terraform. | ||
|
||
```console | ||
$ ecspresso delete --terminate | ||
$ terraform destroy | ||
``` |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,63 @@ | ||
resource "aws_lb" "main" { | ||
name = var.project | ||
internal = false | ||
load_balancer_type = "application" | ||
security_groups = [ | ||
aws_security_group.alb.id, | ||
aws_security_group.default.id, | ||
] | ||
subnets = [ | ||
aws_subnet.public-a.id, | ||
aws_subnet.public-c.id, | ||
aws_subnet.public-d.id, | ||
] | ||
tags = { | ||
Name = var.project | ||
} | ||
} | ||
|
||
resource "aws_lb_target_group" "http" { | ||
for_each = toset(["alpha", "beta"]) | ||
name = "${var.project}-${each.key}" | ||
port = 80 | ||
target_type = "ip" | ||
vpc_id = aws_vpc.main.id | ||
protocol = "HTTP" | ||
deregistration_delay = 5 | ||
|
||
health_check { | ||
path = "/" | ||
port = "traffic-port" | ||
protocol = "HTTP" | ||
healthy_threshold = 2 | ||
unhealthy_threshold = 10 | ||
timeout = 5 | ||
interval = 6 | ||
} | ||
tags = { | ||
Name = "${var.project}-${each.key}" | ||
} | ||
|
||
lifecycle { | ||
create_before_destroy = true | ||
} | ||
} | ||
|
||
resource "aws_lb_listener" "http" { | ||
load_balancer_arn = aws_lb.main.arn | ||
port = 80 | ||
protocol = "HTTP" | ||
|
||
default_action { | ||
type = "forward" | ||
target_group_arn = aws_lb_target_group.http["alpha"].arn | ||
} | ||
|
||
tags = { | ||
Name = "${var.project}-http" | ||
} | ||
} | ||
|
||
output "alb_dns_name" { | ||
value = aws_lb.main.dns_name | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,79 @@ | ||
/* | ||
resource "aws_codedeploy_app" "main" { | ||
name = var.project | ||
compute_platform = "ECS" | ||
} | ||
resource "aws_codedeploy_deployment_group" "main" { | ||
app_name = aws_codedeploy_app.main.name | ||
deployment_config_name = "CodeDeployDefault.ECSAllAtOnce" | ||
deployment_group_name = var.project | ||
service_role_arn = aws_iam_role.codedeploy.arn | ||
auto_rollback_configuration { | ||
enabled = true | ||
events = ["DEPLOYMENT_FAILURE"] | ||
} | ||
blue_green_deployment_config { | ||
deployment_ready_option { | ||
action_on_timeout = "CONTINUE_DEPLOYMENT" | ||
} | ||
terminate_blue_instances_on_deployment_success { | ||
action = "TERMINATE" | ||
} | ||
} | ||
deployment_style { | ||
deployment_option = "WITH_TRAFFIC_CONTROL" | ||
deployment_type = "BLUE_GREEN" | ||
} | ||
ecs_service { | ||
cluster_name = aws_ecs_cluster.main.name | ||
service_name = var.project | ||
} | ||
load_balancer_info { | ||
target_group_pair_info { | ||
prod_traffic_route { | ||
listener_arns = [aws_lb_listener.http.arn] | ||
} | ||
target_group { | ||
name = aws_lb_target_group.http["alpha"].name | ||
} | ||
target_group { | ||
name = aws_lb_target_group.http["beta"].name | ||
} | ||
} | ||
} | ||
} | ||
resource "aws_iam_role" "codedeploy" { | ||
name = "${var.project}-codedeploy" | ||
assume_role_policy = jsonencode({ | ||
Version = "2012-10-17" | ||
Statement = [ | ||
{ | ||
Action = "sts:AssumeRole" | ||
Principal = { | ||
Service = "codedeploy.amazonaws.com" | ||
} | ||
Effect = "Allow" | ||
Sid = "" | ||
} | ||
] | ||
}) | ||
} | ||
data "aws_iam_policy" "codedeploy" { | ||
arn = "arn:aws:iam::aws:policy/AWSCodeDeployRoleForECS" | ||
} | ||
resource "aws_iam_role_policy_attachment" "codedeploy" { | ||
policy_arn = data.aws_iam_policy.codedeploy.arn | ||
role = aws_iam_role.codedeploy.name | ||
} | ||
*/ |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,27 @@ | ||
variable "project" { | ||
type = string | ||
default = "ecspresso" | ||
} | ||
|
||
provider "aws" { | ||
region = "ap-northeast-1" | ||
default_tags { | ||
tags = { | ||
"env" = "${var.project}" | ||
} | ||
} | ||
} | ||
|
||
terraform { | ||
required_version = ">= 1.4.0" | ||
|
||
required_providers { | ||
aws = { | ||
source = "hashicorp/aws" | ||
version = ">= 4.65.0" | ||
} | ||
} | ||
} | ||
|
||
data "aws_caller_identity" "current" { | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,49 @@ | ||
{ | ||
deploymentConfiguration: { | ||
// remove deploymentCircuitBreaker when deployment controller is CODE_DEPLOY | ||
deploymentCircuitBreaker: { | ||
enable: false, | ||
rollback: false, | ||
}, | ||
maximumPercent: 200, | ||
minimumHealthyPercent: 100, | ||
}, | ||
deploymentController: { | ||
type: 'ECS', // ECS or CODE_DEPLOY | ||
}, | ||
desiredCount: 1, | ||
enableECSManagedTags: false, | ||
enableExecuteCommand: true, | ||
healthCheckGracePeriodSeconds: 0, | ||
launchType: 'FARGATE', | ||
loadBalancers: [ | ||
{ | ||
containerName: 'nginx', | ||
containerPort: 80, | ||
targetGroupArn: "{{ tfstate `aws_lb_target_group.http['alpha'].arn` }}", | ||
}, | ||
], | ||
networkConfiguration: { | ||
awsvpcConfiguration: { | ||
assignPublicIp: 'ENABLED', | ||
securityGroups: [ | ||
'{{ tfstate `aws_security_group.default.id` }}', | ||
], | ||
subnets: [ | ||
'{{ tfstate `aws_subnet.public-a.id` }}', | ||
'{{ tfstate `aws_subnet.public-c.id` }}', | ||
'{{ tfstate `aws_subnet.public-d.id` }}', | ||
], | ||
}, | ||
}, | ||
platformFamily: 'Linux', | ||
platformVersion: '1.4.0', | ||
propagateTags: 'SERVICE', | ||
schedulingStrategy: 'REPLICA', | ||
tags: [ | ||
{ | ||
key: 'env', | ||
value: 'ecspresso', | ||
}, | ||
], | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,79 @@ | ||
{ | ||
containerDefinitions: [ | ||
{ | ||
cpu: 0, | ||
essential: true, | ||
image: 'nginx:latest', | ||
logConfiguration: { | ||
logDriver: 'awslogs', | ||
options: { | ||
'awslogs-create-group': 'true', | ||
'awslogs-group': '{{tfstate `aws_cloudwatch_log_group.main.name`}}', | ||
'awslogs-region': '{{ must_env `AWS_REGION` }}', | ||
'awslogs-stream-prefix': 'nginx', | ||
}, | ||
}, | ||
name: 'nginx', | ||
portMappings: [ | ||
{ | ||
appProtocol: '', | ||
containerPort: 80, | ||
hostPort: 80, | ||
protocol: 'tcp', | ||
}, | ||
], | ||
}, | ||
{ | ||
command: [ | ||
'tail', | ||
'-f', | ||
'/dev/null', | ||
], | ||
cpu: 0, | ||
essential: true, | ||
image: 'debian:bullseye-slim', | ||
logConfiguration: { | ||
logDriver: 'awslogs', | ||
options: { | ||
'awslogs-create-group': 'true', | ||
'awslogs-group': '{{tfstate `aws_cloudwatch_log_group.main.name`}}', | ||
'awslogs-region': '{{ must_env `AWS_REGION` }}', | ||
'awslogs-stream-prefix': 'bash', | ||
}, | ||
}, | ||
name: 'bash', | ||
secrets: [ | ||
{ | ||
name: 'FOO', | ||
valueFrom: '{{tfstate `aws_ssm_parameter.foo.name`}}' | ||
}, | ||
{ | ||
name: 'BAR', | ||
valueFrom: '{{tfstate `aws_secretsmanager_secret.bar.arn`}}' | ||
}, | ||
{ | ||
name: 'JSON_KEY', | ||
valueFrom: '{{tfstate `aws_secretsmanager_secret.json.arn`}}:key::' | ||
}, | ||
], | ||
}, | ||
], | ||
cpu: '256', | ||
ephemeralStorage: { | ||
sizeInGiB: 30, | ||
}, | ||
executionRoleArn: '{{tfstate `aws_iam_role.ecs-task.arn`}}', | ||
family: 'ecspresso', | ||
memory: '512', | ||
networkMode: 'awsvpc', | ||
requiresCompatibilities: [ | ||
'FARGATE', | ||
], | ||
tags: [ | ||
{ | ||
key: 'env', | ||
value: 'ecspresso', | ||
}, | ||
], | ||
taskRoleArn: '{{tfstate `aws_iam_role.ecs-task.arn`}}', | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,6 @@ | ||
resource "aws_ecs_cluster" "main" { | ||
name = var.project | ||
tags = { | ||
Name = var.project | ||
} | ||
} |
Oops, something went wrong.