Follow

Keep Up to Date with the Most Important News

By pressing the Subscribe button, you confirm that you have read and are agreeing to our Privacy Policy and Terms of Use
Contact

Conditionally creating load balancer with ecs service in Terraform

I’m loosely following this example to create a multiple ECS services under one cluster: https://github.com/shashimal/terraform-ecs/blob/master/main.tf

The problem I have is that only some of the services will require a load balancer in front of the service.

I have tried adding a flag (alb_enabled) into the service_config variable like so:

MEDevel.com: Open-source for Healthcare and Education

Collecting and validating open-source software for healthcare, education, enterprise, development, medical imaging, medical records, and digital pathology.

Visit Medevel

service_config = {
  "test-service-efs" = {
    auto_scaling = {
      scale_in = {
        max_capacity = 1
        min_capacity = 1
        schedule = "00 16 * * ? 2199"
      }
      scale_out = {
        max_capacity = 1
        min_capacity = 1
        schedule = "00 16 * * ? 2199"
      }
    }
    desired_count = 1
    is_public = false
    name = "test-service-efs"

    alb_enabled = false
  }
}
resource "aws_ecs_service" "ecs_service" {
  for_each        = var.service_config
  name            = "${each.value.name}-service"
  cluster         = aws_ecs_cluster.ecs_cluster.id
  task_definition = aws_ecs_task_definition.ecs_task_definition[each.key].arn
  launch_type     = "FARGATE"
  desired_count   = each.value.desired_count

  network_configuration {
    subnets          = var.private_subnets
    assign_public_ip = each.value.is_public 
    security_groups  = var.security_groups
  }

  load_balancer {
    target_group_arn = aws_alb_target_group.alb_target_group[each.key].arn
    container_name   = each.value.name
    container_port   = 3000
  }

  lifecycle {
    ignore_changes = [task_definition,
      tags,
      desired_count
    ]
  }
  tags = var.tags
}

#Dynamically create the alb target groups for app services
resource "aws_alb_target_group" "alb_target_group" {
  for_each = { for k, v in var.service_config : k => v if v.alb_enabled }
  name = "${each.value.name}-tg"
  port = 3000
  protocol = "HTTP"
  target_type = "ip"
  vpc_id = "vpc-xxxxxxxxxxxx"
}

This works fine when the flag is enabled. However when I disable this flag, due to the target group not existing, the ecs_service load balancer fails

Error: Invalid index
on modules\ecs\main.tf line 79, in resource "aws_ecs_service" "ecs_service":
  79:     target_group_arn = aws_alb_target_group.alb_target_group[each.key].arn
    aws_alb_target_group.alb_target_group is object with no attributes
    each.key is "test-service-efs"
The given key does not identify an element in this collection value

I completely understand why this is failing, but I’m struggling to figure out a workaround for it. I was thinking of having two separate ecs modules which create services with and without a load balancer but this could get messy when trying to pass in the various rules to the ALB as variables. There doesn’t seem to be a way to set the conditional within the load_balancer section in aws_ecs_service but was wondering does anybody have any creative workarounds for this?

>Solution :

You have to use dynamic blocks to create your block optional:

 dynamic "load_balancer" {
    for_each = var.service_config[each.key] == true ? [1]: []
    content {
      target_group_arn = aws_alb_target_group.alb_target_group[each.key].arn
      container_name   = each.value.name
      container_port   = 3000
    }
  }
Add a comment

Leave a Reply

Keep Up to Date with the Most Important News

By pressing the Subscribe button, you confirm that you have read and are agreeing to our Privacy Policy and Terms of Use

Discover more from Dev solutions

Subscribe now to keep reading and get access to the full archive.

Continue reading