We are very close from testing our scaling rules. Before we create an ECS Service, there are a few things we need to do. First we need to building a container image and store it into ECR and then create an ECS task definition in preparation for our ECS Service.
We need an application to scale!. In this section we will build a Docker image using a simple python flask-based web application and deploy in our ECS cluster using ECR (Amazon Elastic Container Registry). CloudFormation deployment has already created an entry in the ECR registry that we will use to store our webapp container image.
Execute the lines below. This might take a couple of minutes. The lines below:
export ECR_REPO_URI=$(aws ecr describe-repositories --repository-names ecs-spot-workshop/webapp | jq -r '.repositories[0].repositoryUri')
aws ecr get-login-password --region $AWS_REGION | docker login --username AWS --password-stdin $ECR_REPO_URI
cd ~/environment/ec2-spot-workshops/workshops/ecs-spot-capacity-providers/webapp/
docker build --no-cache -t ecs-spot-workshop/webapp .
docker tag ecs-spot-workshop/webapp:latest $ECR_REPO_URI:latest
docker push $ECR_REPO_URI:latest
When creating new services, the service will make a reference to what type of tasks are launched within the service, hence we need to register
a task definition
. We have prepared a simple task definition that uses the container image we just created and sets a few parameters such as
the resource required (CPU/Memory) and the ports that will be exposed.
Run the following section. This creates a copy the template ECS Task from templates/ec2-task.json to the current directory and substitutes the template with the actual value of the docker image path. Finally it registers the task so it can be used by Services or deployed to ECS clusters.
cd ~/environment/ec2-spot-workshops/workshops/ecs-spot-capacity-providers/
cp -Rfp templates/ec2-task.json .
sed -i -e "s#DOCKER_IMAGE_URI#$ECR_REPO_URI:latest#g" ec2-task.json
aws ecs register-task-definition --cli-input-json file://ec2-task.json
The task definition will look like this in the console:
To create the service, follow these steps:
It may take up to a couple of mintues for the capacity to be provisioned and the task to be running. You can check the CloudWatch Dashboard or the C3VIS tool that we used in the previous sections to check out for changes in the cluster once the service is created.
Question: Given the Capacity Provider Strategy in use (OnDemand Capacity Provider Base=2, weight=1
, Spot Capacity Provider Base=0, weight=3
), Could you predict how many out of the 10 tasks will be running in Spot instances versus how many will be running on OnDemand Instances?
The CLI can help you to provide details of how tasks are spread across capacity providers. You can use aws ecs describe-tasks
to validate your response.
Given the split OnDemand Capacity Provider Base=2, weight=1
, Spot Capacity Provider Base=0, weight=3
, we should expect
The tasks should distributed as OnDemand = 4 tasks and Spot =6 tasks. We can veryfy it by running the following command in the Cloud9 terminal
export cluster_name=EcsSpotWorkshop
export service_name=ec2-service-split
aws ecs describe-tasks \
--tasks $(aws ecs list-tasks --cluster $cluster_name \
--service-name $service_name --query taskArns[*] --output text) \
--cluster $cluster_name \
--query 'sort_by(tasks,&capacityProviderName)[*].{TaskArn:taskArn,CapacityProvider:capacityProviderName,Instance:containerInstanceArn,AZ:availabilityZone,Status:lastStatus}' \
--output table
Your results should be similar to the ones below: