DEV Community

leotoras
leotoras

Posted on

AWS ECS - Let's play with it

Lets start talking about AWS ECS service, what it is, what it does and so on.

For this article, lets assume that you already have a basic knowledge about containers and how they work (if not, please take a look at ).

So, ECS states for Elastic Container Service and it is a container orchestration service where you can launch your container applications in an easily manner. It makes activities like deploy, manage and scale the applications much more easier.
As it is a service, you really don't need to worry or concern about hardware infrastructure, which is totally managed by AWS (as said, it is a fully managed service). In other words, if you want to run your containerized application on AWS without worry about infrastructure management, ECS is the right option.

To make things easier than before ECS is also fully integrated with AWS ECR (Elastic Container Registry), which is another AWS fully managed AWS service to push your container images. If you are used with Docker Hub, don't worry, it works as well !

We are ready to start, so first things first. Now it is time to visit the AWS ECR service :-)

When you work with ECS, you have 3 options for computing capacity. They are EC2 instances, Fargate and ECS Anywhere (using on premise resources). Lets explain a little bit about each one:

  • EC2 instances: this type uses EC2 instances to have your services and tasks running, so you need to choose the instance family, instance size, number of instances and so on. In thi case, the instances are customized for ECS service and have the ecs-agent running on top of them.
  • Fargate: this type of compute capacity is also know as serverless because you don't have EC2 instances to manage. You simply put your services and tasks to run and nothing else.
  • ECS Anywhere: this type of compute is the ability to register on premise servers to your ECS cluster (we will not touch on this inn this article !).

If you are in doubt on what type of compute capacity you use, you can take a look at this document: .

To make things simple, lets work with Fargate compute mode to run our containers. To start with that, first of all we need an ECS cluster, so lets create one. We have a lot of option to create our cluster, using AWS console, using CLI, using AWS SDK and other IaC tools like CloudFormation and Terraform for example. In our case, lets make it simple and use CLI.
Simply issue this command:

aws ecs create-cluster --cluster-name devto-ecs-cluster --capacity-providers FARGATE
Enter fullscreen mode Exit fullscreen mode

You should have an output like that:

Image description

To make sure the cluster is there, you can list it:

aws ecs list-clusters
Enter fullscreen mode Exit fullscreen mode

You are able to see out cluster:

Image description

Now, our cluster is up and running, cool ! The next step is to create a task definition for our containers, but what is that ? Let me explain.

Task Definition is a text file in JSON format that describes the containers and their parameters that will be part of the application. The parameters include CPU, memory, image name, IAM role, logging information and much more. You can visit this to take a deeper look on task definitions.

That said, lets create out task definition. You can use any text editor, in my case I use vi to create a JSON file called devto-task-definition, like following:

{
    "containerDefinitions": [
        {
            "name": "devto-article-container",
            "image": "<your_account_id>.dkr.ecr.us-east-1.amazonaws.com/my-ecs-container-repo",
            "cpu": 0,
            "portMappings": [
                {
                    "name": "devto-article-container-80-tcp",
                    "containerPort": 80,
                    "hostPort": 80,
                    "protocol": "tcp",
                    "appProtocol": "http"
                }
            ],
            "essential": true,
            "environment": [],
            "environmentFiles": [],
            "mountPoints": [],
            "volumesFrom": [],
            "ulimits": [],
            "logConfiguration": {
                "logDriver": "awslogs",
                "options": {
                    "awslogs-create-group": "true",
                    "awslogs-group": "/ecs/devto-task-definition",
                    "awslogs-region": "us-east-1",
                    "awslogs-stream-prefix": "ecs"
                }
            }
        }
    ],
    "family": "devto-task-definition",
    "taskRoleArn": "arn:aws:iam::<your_account_id>:role/EcsTaskRole",
    "executionRoleArn": "arn:aws:iam::<your_account_id>:role/ecsTaskExecutionRole",
    "networkMode": "awsvpc",
    "volumes": [],
    "placementConstraints": [],
    "requiresCompatibilities": [
        "FARGATE"
    ],
    "cpu": "256",
    "memory": "512",
    "runtimePlatform": {
        "cpuArchitecture": "X86_64",
        "operatingSystemFamily": "LINUX"
    }
}
Enter fullscreen mode Exit fullscreen mode

"Pay attention that I replaced my account id by the string . In your case, it should be your own account id."

With the task definition file created, we need to register this task definition so ECS is able to reference when creating a service or task. To do that, just issue the following command:

aws ecs register-task-definition --cli-input-json file://devto-task-definition.json
Enter fullscreen mode Exit fullscreen mode

To make sure the task definition has been successfully created, you can issue the command to confirm:

aws ecs list-task-definitions

Image description

With the task definition registered, we are finally able to run our task in our ECS cluster (Uhuuuuulll !!!). To do that, lets create a service to run our task and test it from a browser on the internet. To do that, take note about the subnet-id you will deploy the service, the security group for that service (as this is an example, lets use a security group allowing access from internet on port 80) and lets assign a public IP to that, so we will be able to test it from anywhere. With all required information, lets simply issue the following command:

aws ecs create-service --cluster devto-ecs-cluster \
--service-name devto-article-service \
--task-definition devto-task-definition \
--desired-count 1 \
--launch-type "FARGATE" \
--network-configuration "awsvpcConfiguration={subnets=[subnet-014d9c5f9d0bb9b90],securityGroups=[sg-03eb793e06078aabe],assignPublicIp=ENABLED}"
Enter fullscreen mode Exit fullscreen mode

To make sure the service has been created, lets list the services running in our ECS cluster with the following command:

aws ecs list-services --cluster devto-ecs-cluster
Enter fullscreen mode Exit fullscreen mode

Yes, our service is right there:

Image description

Now our container app is running in a service on top of the ECS cluster, that is great !!! So, time to test it. As we deployed in a public subnet to make it available to test in the internet, we need to find the public IP address that was assigned to out task in the service. To grab this information, lets run some commands !

First, lets list our task to get the arn. Issue the following command:

aws ecs list-tasks --cluster devto-ecs-cluster --service devto-article-service
Enter fullscreen mode Exit fullscreen mode

It will output the task arn:

Image description

Now, lets describe this task using the arn, so we will be able to check which network interface it is using and with that information, check the public IP assigned to the task. Just issue the following command:

aws ecs describe-tasks \
--cluster devto-ecs-cluster \
--tasks arn:aws:ecs:us-east-1:<your_account_id>:task/devto-ecs-cluster/defc81a93bda4df6ad73957ef718876e
Enter fullscreen mode Exit fullscreen mode

"Pay attention that I replaced my account id by the string . In your case, it should be your own account id."

Look for the "networkInterfaceId" value as shown bellow:

Image description

With the network interface id, we can easily discover the IP address with a describe command. Just issue the following command:

aws ec2 describe-network-interfaces \
--network-interface-id eni-0765281dfd52d2b06
Enter fullscreen mode Exit fullscreen mode

The output will be as shown bellow:

Image description

What amaaaaazing news !!! Now we can test our application from a browser and make sure it is running as expected. So what are we waiting for ? Lets try it right now !!! Lets put the public IP in a browser and have our fingers crossed:

Image description

Uaaaaauuuu !!! After some commands, we are finally done with our mission to have a container application running on a ECS cluster as required.

You did a great job. Thank you so much for follow me in this article and see you in the next.

sources:
https://aws.amazon.com/getting-started/hands-on/deploy-docker-containers/
https://docs.aws.amazon.com/AmazonECS/latest/developerguide/create-container-image.html
https://docs.aws.amazon.com/AmazonECS/latest/developerguide/Welcome.html
https://docs.aws.amazon.com/AmazonECS/latest/developerguide/ECS_AWSCLI_Fargate.html#ECS_AWSCLI_Fargate_register_task_definition

Top comments (0)