Develop Code & Deploy to AWS Fargate Using Visual Studio Code
TL;DR
- Learn how to deploy any Docker container to AWS Fargate using Fargate CLI.
- This tutorial utilizes Visual Studio Code Development Container because it can provide an environment with all the necessary tools on your local machine without much hassle. It can also be reused for other tool chains.
A tutorial using a forked Fargate CLI tool
In my last post, we have gone through the exercise of building and deploying a Lambda service using the AWS SAM CLI via VS Code. In today’s post, I am sharing a similar approach in using the Fargate CLI to deploy a dockerized container services using Amazon Fargate.
There are similar tutorials that demonstrate the use of the Fargate CLI. However, there are some nuances in using the CLI and some inconsistencies in the flows that have to be addressed in its implementation.
I found an issue which impede new users to begin understanding and using the Fargate CLI:
- The Fargate CLI currently does not check if the default security groups exist. It polls for the
fargate-default
security group. For newly created AWS accounts, there is no such Security Group. This results in anil
being returned. The CLI continues down this path to register the task/service with the SG, resulting in messages that do not easily identify the root cause of the error.
This tutorial uses the forked version of the Fargate CLI that I have created. Pull Requests have already been made against the original repository to fix this issue and to improve the usability of the CLI, lowering the learning curve for new users to the CLI tool.
And finally, all required development/deployment tools is defined within the Dockerfile
of the project (Java/Node). This can be a basis for any new projects that you want to embark on.
Setting up the environment
The premise of this tutorial is that all tools needed to deploy AWS Fargate services are available in a Development Container.
This tutorial leverages the Development Container and steps that were shared in my previous post. Feel free to follow through until the following sections
By the end of those sections, you would have VS Code and AWS environment set up with access to the AWS and Fargate CLI command line tools.
Deploying a sample container as a Fargate application
Before proceeding, it is important to note that the provided environment has been set up to:
- Forward your local host ssh agent to the remote container. This is handled by VS Code.
- Share the aws credential and config files from your local host with the remote container. This is configured via the
.devcontainer/devcontainer.json
file in the project.
There are 2 ways to run Fargate applications.
- Tasks are one-time execution of your containers. Containers are not reinstantiated after it exits.
- Services are managed containers that get restarted if a failure occurs. It can also be scaled up or down to the number of containers that is needed.
Tasks
Run the following command to use a public image (nginx
for this post’s example)
$ fargate task run web --image nginx:latest
Check out the running task and its ip address, and test out the endpoint
$ fargate task ps web
ID IMAGE STATUS RUNNING IP CPU MEMORY
2912399f-e5a2-4504-a9e5-730f3a019bb8 nginx:latest running 58s <readact> 256 512
$ curl <redacted>
<!DOCTYPE html>
<html>
<head>
<title>Welcome to nginx!</title>
...
You can also check out the logs
$ fargate task logs web
fargate/web/2912399f-e5a2-4504-a9e5-730f3a019bb8 <redacted> - - [08/Jun/2020:09:29:43 +0000] "GET / HTTP/1.1" 200 612 "-" "curl/7.64.0" "-"
Once you are done, destroy/close the task by using
$ fargate task stop web
Services
An additional step is required to deploy Fargate services. First you need to create a load balancer.
$ fargate lb create mylb --port 80
[i] Created load balancer mylb
Next, deploy the container as a Fargate service and assign it to the load balancer at port 80.
$ fargate service create myapp --image nginx:latest --lb mylb --port 80
[i] Created service myapp
Check out the running container and its ip address, and test out the endpoint
$ fargate service ps myapp
ID IMAGE STATUS RUNNING IP CPU MEMORY
8cb7ea13-2f5f-4deb-89d9-fb955b26b2d2 nginx:latest running 1m8s <redacted> 256 512
$ curl <readacted>
<!DOCTYPE html>
<html>
<head>
<title>Welcome to nginx!</title>
...
Destroying the Fargate service is slightly more involved. You would need to scale down the container instances before deleting both the service and its load balancer.
$ fargate service scale myapp 0
[i] Scaled service myapp to 0
$ fargate service destroy myapp
[i] Destroyed service myapp
$ fargate lb destroy mylb
[i] Destroyed load balancer mylb
Caveat
Please note (again) that this project uses a forked version of the AWS Fargate CLI that has several issues fixed.
Summary
So, what have we deployed so far?
The Fargate CLI by default uses the fargate
ECS cluster as well as the fargate-default
security group for deploying container applications. If these are not available, the CLI sets and creates these entities.
We have created a Fargate Service (myapp
) and a load balancer (mylb
) for incoming traffic that will support load balancing against a cluster of containers. We have also create a single Fargate Task (web
) which is actually a 1 time job execution.
And all of this is done in a containerized development environment within Visual Studio Code!
Feel free to take a look at how this has been set up in .devcontainer/devcontainer.json
and Dockerfile
of the project (Java/Node).
Hopefully this helps you try out AWS Fargate (it really helped me) and to see how VS Code development container environment helps new individuals to the project get productive immediately.
Feedback is always welcome in the comment section.