Categories
AWS Bash

Deploy a docker image from AWS ECR registry to Elastic Beanstalk in 2 minutes

In this tutorial, we will see how to deploy a docker image that is stored in AWS ECR registry to AWS Elastic Beanstalk. We will use automated scripts using the AWS CLI.

0) Prerequisites

You need AWS CLI installed on your machine. Follow this tutorial to do it in 30 seconds. Also you need a docker image in AWS ECR registry. Go to this url:

https://us-west-2.console.aws.amazon.com/ecr/repositories?region=us-west-2

to create a repository, and then follow the push commands to push your docker image.

1) Dockerrun.aws.json and trust-policy.json

Open a work folder where you will execute the AWS CLI and create files. In this folder, create a file named Dockerrun.aws.json, with following content:

{
  "AWSEBDockerrunVersion": "1",
  "Image": {
    "Name": "<dockerImageURI>",
    "Update": "true"
  },
  "Ports": [
    {
      "ContainerPort": "<containerPort>"
    }
  ]
}

(replace <dockerImageURI> with the URI of your docker image stored in ECR registry, and <containerPort> with the port of your container, 8080 or 80 for instance).

Then, still in your work folder, create a file called trust-policy.json, with following content:

{
  "Version": "2008-10-17",
  "Statement": [
    {
      "Effect": "Allow",
      "Principal": {
        "Service": "ec2.amazonaws.com"
      },
      "Action": "sts:AssumeRole"
    }
  ]
}

2) Create the IAM role

We need an IAM role that will have access to EC2, Elastic Beanstalk and ECR registry. We will call this role ec2-role. To create it, run in your work folder:

aws iam create-role --role-name ec2-role --assume-role-policy-document file://trust-policy.json
aws iam attach-role-policy --policy-arn arn:aws:iam::aws:policy/AdministratorAccess-AWSElasticBeanstalk --role-name ec2-role
aws iam attach-role-policy --policy-arn arn:aws:iam::aws:policy/AmazonEC2ContainerRegistryReadOnly --role-name ec2-role
aws iam create-instance-profile --instance-profile-name ec2-role
aws iam add-role-to-instance-profile --instance-profile-name ec2-role --role-name ec2-role

3) Set AWS cli_pager

To simplify the CLI output, do:

aws configure set cli_pager ""

4) Upload the Elastic Beanstalk application

We will zip the file Dockerrun.aws.json from step 1) and upload it to a S3 bucket (that you need to create here if you don’t already have one).

s3_bucket=springboot77
region=us-west-2
app_name=spring-boot
app_version=3.0

zip -r springboot.zip Dockerrun.aws.json
aws s3 cp springboot.zip s3://$s3_bucket/springboot2.zip
aws elasticbeanstalk create-application --application-name $app_name --region $region
aws elasticbeanstalk create-application-version --application-name $app_name --version-label $app_version \
    --source-bundle S3Bucket=$s3_bucket,S3Key=springboot2.zip --region $region

(in the above bash, replace region, app_name, app_version and s3_bucket with your own values). During the zip step, you could also add a folder .ebextensions with *.config files inside, to setup HTTPS termination for isntance.

5) Create the Elastic Beanstalk environment and deploy the docker app

region=us-west-2
app_name=spring-boot
app_version=3.0
env_name=docker-linux-20

aws elasticbeanstalk create-environment --environment-name $env_name --cname-prefix springbb --application-name $app_name  \
    --version-label $app_version --solution-stack-name "64bit Amazon Linux 2 v3.4.5 running Docker" --region $region \
    --option-settings '[
      {
        "Namespace": "aws:autoscaling:launchconfiguration",
        "OptionName": "InstanceType",
        "Value": "t2.micro"
      },
      {
        "Namespace": "aws:autoscaling:launchconfiguration",
        "OptionName": "IamInstanceProfile",
        "Value": "ec2-role"
      },
      {
        "Namespace": "aws:elasticbeanstalk:environment",
        "OptionName": "LoadBalancerType",
        "Value": "application"
      }
    ]'

(replace region, app_name, app_version and env_name with your own values).

Now, if you go to the Elastic Beanstalk console in the AWS console on region us-west-2, you should see your docker app. Also you can find there the app HTTP URL, and you should be able to access it with cURL or your browser.

6) Update your Elastic Beanstalk environment with a new docker image

Let’s say you now have a new docker image URI that you want to deploy. Go back to step 1) and replace <dockerImageURI> in Dockerrun.aws.json with your new docker image URI. Then run:

s3_bucket=springboot77
region=us-west-2
app_name=spring-boot
app_version=4.0
env_name=docker-linux-20

zip -FSr springboot.zip Dockerrun.aws.json
aws s3 cp springboot.zip s3://$s3_bucket/springboot2.zip
aws elasticbeanstalk delete-application-version --application-name $app_name --version-label $app_version --region $region
aws elasticbeanstalk create-application-version --application-name $app_name --version-label $app_version \
    --source-bundle S3Bucket=$s3_bucket,S3Key=springboot2.zip --region $region
aws elasticbeanstalk update-environment --environment-name $env_name --version-label $app_version --region $region

(in the above bash, replace region, app_name, app_version, s3_bucket and env_name with your own values)

Your new app_version should now be deployed ! That’s it for this tutorial, thank you for reading. If you have any question, please leave a reply below, we answer within 24 hours.

Leave a Reply

Your email address will not be published. Required fields are marked *