Search code examples
amazon-web-servicesaws-cdk

How to setup ECS with two active container ports


I have a docker image with 2 ports exposed, 5000 for backend and 4200 for front-end and I use PM2 to start the 2 services (docker works locally fine), am trying to build cdk for that, in the ECS service log, I can see that PM2 has started the 2 services and they should be running as expected, bu,in the deployment tab, the stack gets stuck with error

service express-app-service instance i-09364a536df663f23 port 4200 is unhealthy in target-group Expres-ECSAL-HAHCQJM1YTBJ due to (reason Health checks failed)

  1. I'd like to know how can I set health check properly (should be for the 2 ports ?) given that I have 2 ports (I already have health check point in the backend).

  2. how can I make 443 requests directs to port 4200(front-end) ?

these are code snippets of what I have now

const container = taskDefinition.addContainer("AppContainer", ..)
container.addPortMappings(
      {
        containerPort: 5000,
        hostPort: 5000,
        protocol: ecs.Protocol.TCP
      },
      {
        containerPort: 4200,
        hostPort: 4200,
        protocol: ecs.Protocol.TCP
      }
    )



const listener = ecsALB.addListener('HttpListener', {
      certificates: [sslCertificate],
      protocol: elbv2.ApplicationProtocol.HTTPS,
      sslPolicy: elbv2.SslPolicy.FORWARD_SECRECY_TLS12_RES,
      port: 443,
    });


    /**
     * Set that requests coming into our listener should be
     * redirected to our service containers (express servers).
     */
    listener.addTargets('ECS_ALB_ServerTarget', {
      port: 443,
      healthCheck: {
        path: "/signin",
        enabled: true,
        protocol: ecs.Protocol.HTTP
      },
      protocol: elbv2.ApplicationProtocol.HTTP,
      targets: [service.loadBalancerTarget({
        containerName: 'express-app-container',
        containerPort: 4200,
      })],
    });

Solution

  • Answers to your questions:

    1. Usually the port mapping of your container is used when performing the health check. So the endpoint for doing the health check in your case will be something like

      http://<ecs-container-ip>:4200/signin

      if this is successful and returns a http code 200, the health check passes.

    2. Yes, it is possible and is usually the case. The HTTPS (443) connection is terminated on the load balancer and a new connection is initiated towards your ECS container.

    I think you should update the target port to the following, which is pointing to your frontend.

    listener.addTargets('ECS_ALB_ServerTarget', {
          port: 4200,
          ...
    

    Port is defined as such:

    The port on which the target receives traffic.

    It is also worth checking if the security group of the container is allowing for incoming traffic on port 4200 from the load balancer.

    targets: [service.loadBalancerTarget({
    

    The code above is registering the container with the target group which was created.