+++ title = "Deploying Rust App with Terraform on AWS Fargate" description = "Learn how to deploy a Loco app with Terraform (IaC). Generate a deployment with Loco generators and set it up step-by-step." date = 2023-12-20T16:04:40+00:00 updated = 2023-12-16T04:20:40+00:00 draft = false template = "blog/page.html" [taxonomies] authors = ["Antonio Souza"] +++ In today's rapidly evolving technological landscape, Infrastructure as Code (IaC) has become a cornerstone for efficient, scalable, and maintainable cloud infrastructure deployment. IaC involves managing and provisioning computing infrastructure through machine-readable script files, rather than through physical hardware configuration or interactive configuration tools. This allows for the automation of infrastructure deployment and management, which in turn reduces the risk of human error and increases the speed of deployment. In this article, we will explore how to deploy a Rust app built with [loco](https://loco.rs) on AWS Fargate using Terraform. We will start by creating a new project and selecting the `Rest API` template: ````sh ```sh $ cargo install loco $ loco new ✔ ❯ App name? · myapp ? ❯ What would you like to build? › lightweight-service (minimal, only controllers and views) ❯ Rest API (with DB and user auth) SaaS app (with DB and user auth) ```` ## Prerequisites To deploy our app on AWS Fargate, we will need to have the following tools installed: - [Docker](https://docs.docker.com/get-docker/) - Docker is a containerization platform that allows you to package your application and all of its dependencies into a standardized unit for software development. - [Terraform](https://learn.hashicorp.com/tutorials/terraform/install-cli) - Terraform is an open-source infrastructure as code software tool that enables you to safely and predictably create, change, and improve infrastructure. - [AWS CLI](https://docs.aws.amazon.com/cli/latest/userguide/install-cliv2.html) - The AWS Command Line Interface (CLI) is a unified tool to manage your AWS services. ## Creating the Docker Image To create the Docker image for our app, we will use the loco CLI. The `cargo loco generate deployment` command will create a Docker image for our app. It will also create a `Dockerfile` for us, which we can use to build the image. ```sh $ cargo loco generate deployment ? ❯ Choose your deployment › ❯ Docker Shuttle added: "dockerfile" added: ".dockerignore" ``` Now, we can build the Docker image which will be used to deploy our app on AWS Fargate. ```sh $ docker build -t myapp . [+] Building 237.1s (16/16) FINISHED docker:desktop-linux => [internal] load build definition from dockerfile 0.0s => => transferring dockerfile: 331B 0.0s ... => => writing image sha256:07416ca8195e4026ab65bc567f990ea83141aa10890f8443deb8f54a8bae7f0a 0.0s => => naming to docker.io/library/myapp ``` ## Setting up AWS To deploy our app on AWS Fargate, we will need to create an AWS account and set up the AWS CLI. You can create an AWS account [here](https://portal.aws.amazon.com/billing/signup#/start/email). You will also need to install the AWS CLI. You can find instructions on how to do this [here](https://docs.aws.amazon.com/cli/latest/userguide/install-cliv2.html). Finally, you need to create an IAM user to use with the AWS CLI. You can find instructions on how to do this [here](https://docs.aws.amazon.com/IAM/latest/UserGuide/id_users_create.html). Now, we can configure the AWS CLI with the credentials of the IAM user we just created. ```sh $ aws configure AWS Access Key ID [None]: AWS Secret Access Key [None]: Default region name [None]: Default output format [None]: json ``` ## Creating the repository on ECR To deploy our app on AWS Fargate, we will need to create a repository on ECR. You can do this by running the following command: ```sh $ aws ecr create-repository --repository-name myapp { "repository": { "repositoryArn": "arn:aws:ecr:us-east-1:123456789012:repository/myapp", "registryId": "123456789012", "repositoryName": "myapp", "repositoryUri": "123456789012.dkr.ecr.us-east-1.amazonaws.com/myapp", "createdAt": 1627981234.0, "imageTagMutability": "MUTABLE", "imageScanningConfiguration": { "scanOnPush": false } } } ``` ## Pushing the Docker image to ECR Now, we can push the Docker image to ECR. You can do this by running the following commands: -1. Log in to ECR ```sh $ aws ecr get-login-password --region us-east-1 | docker login --username AWS --password-stdin 123456789012.dkr.ecr.us-east-1.amazonaws.com ``` -2. Tag the Docker image ```sh $ docker tag myapp:latest 123456789012.dkr.ecr.us-east-1.amazonaws.com/myapp:latest ``` -3. Push the Docker image to ECR ```sh $ docker push 123456789012.dkr.ecr.us-east-1.amazonaws.com/myapp:latest ``` ## Creating the main.tf file for Terraform This is the main Terraform file that will be used to deploy our app on AWS Fargate. It will create the following resources: ```hcl terraform { required_providers { aws = { source = "hashicorp/aws" version = "~> 4.0" } archive = { source = "hashicorp/archive" version = "~> 2.2.0" } } required_version = "~> 1.0" } # Configure the AWS Provider provider "aws" { region = "us-east-1" // Change this to your region access_key = "" // Change this to your access key secret_key = "your secret key" // Change this to your secret key } resource "aws_ecr_repository" "myapp" { name = "myapp" } resource "aws_ecs_cluster" "myapp_cluster" { name = "myapp_cluster" } resource "aws_cloudwatch_log_group" "myapp" { name = "/ecs/myapp" } resource "aws_ecs_task_definition" "myapp_task" { family = "myapp-task" container_definitions = <