TL;DR; If you are using Amazon EC2 Container Registry for your Docker images, you are probably aware that you have to use Docker login for the registry via the Amazon Web Services (AWS) Command Line Interface (CLI) utility. This implies that you have to install and configure the AWS CLI and its dependency (Python), however, there are alternatives that do not require installing the AWS CLI.
Background
The Amazon EC2 Container Registry (Amazon ECR) became generally available in 2015. It was a welcome addition to the Amazon Web Services product set, as it allowed AWS customers to host private container registries. The general goal behind Amazon ECR was to simplify development and production workflows. For me, this goal was successfully accomplished, with one caveat: I have to install and run additional tools on my machine, tools I otherwise not need. One such tool is the AWS CLI utility. While the AWS CLI is great and indispensable for those who live and breathe Amazon EC2, there may be cases when not everyone needs this utility or perhaps should not have a CLI access level. This is especially true for larger organizations.
Assuming I have Docker installed if I ran docker pull
without first logging into the ECR Docker registry, I will get the following :
$docker pull my-aws-account.dkr.ecr.us-west-2.amazonaws.com/foo:latest Pulling repository my-aws-account.dkr.ecr.us-west-2.amazonaws.com/foo:latest unauthorized: authentication required
In order to obtain the Docker login, I must first install and configure the AWS CLI utility, which in turn per the AWS CLI user guide, requires first installing Python 2 version 2.6.5+ or Python 3 version 3.3+.
Even with the AWS CLI installed, I have to make sure that the version of CLI plays well with Docker version to avoid:
“Unknown options: –no-include-email”
After the AWS CLI is installed and configured, using the Docker against Amazon ECR is pretty straightforward and no different from other container registries, with an occasional login refresh (depending on your security configuration):
eval $(aws ecr get-login --region my-region)
AWS CLI in Docker
To avoid installing AWS CLI on my machine, the next best thing is to run the AWS CLI inside the Docker container. Quite a few publicly available AWS CLI docker images are available on dockerhub.com, but for one reason or another, none of them exactly satisfied my needs (I’m picky), so I did what everybody else does: created my own illya/aws-cli.
FROM python:2.7-slim ENV VERSION=1.11.136 RUN apt-get update \ && apt-get install -y --no-install-recommends \ && apt-get install --reinstall groff-base \ && mkdir -p /aws \ && pip install -U pip \ && pip install awscli==${VERSION} \ && rm -rf /var/lib/apt/lists/* WORKDIR /aws ENTRYPOINT ["aws"]
With this image, if I need to get the Docker login, all I have to do is run:
eval $(docker run --rm -v $HOME/.aws:/root/.aws:ro illya/aws-cli ecr get-login --region us-west-2)
Moreover, this image supports all AWS CLI subcommands available for a given CLI version:
docker run --rm -v $HOME/.aws:/root/.aws:ro aws-cli ec2 describe-vpcs --region=us-east-1
I can even use it to configure the AWS CLI credentials for my machine. For more examples and details please refer to README.md
Amazon ECR Docker Credential Helper
AWS Labs released ECR Credentials Helper (written in Go), which seamlessly integrates with the Docker daemon and makes it easier to use Amazon ECR by leveraging Docker’s Credential Helper Protocol.
The Credential Helper does require a couple of things:
- Golang 1.6+
- Docker 1.11+
Golang
Per golang.org – “Go is an open source programming language that makes it easy to build simple, reliable, and efficient software”. If you’ve never tried it, you totally should. Installing Go itself is simple and it is very straightforward follow the Install the Go tools from the Golang Getting Started documentation page.
Docker
If you are running a Docker version earlier than 1.11, you should probably upgrade it, regardless of ECR.
Configuration
I followed the instructions from the repository README.md to install and configure my $HOME/.docker/config
against two AWS regions: [us-east-1] and [us-west-2], which ended up looking like this:
{ "credsStore": "ecr-login", "credHelpers": { "my-aws-account.dkr.ecr.us-west-2.amazonaws.com": "ecr-login", "my-aws-account.dkr.ecr.us-east-1.amazonaws.com": "ecr-login" } }
To verify that I don’t have afoo
image in my local Docker registry:
docker images my-aws-account.dkr.ecr.us-west-2.amazonaws.com/foo:latest REPOSITORY TAG IMAGE ID CREATED SIZE
Now, the moment of truth:
docker pull my-aws-account.dkr.ecr.us-west-2.amazonaws.com/foo:latest latest: Pulling from foo 9e1d18812a0d: Already exists f49ebe34919a: Already exists ... 451b4fbc9616: Pull complete 361b5c020933: Pull complete Digest: sha256:86df90592794c3f8d54d2c6969863abeef3b1d66bed603a6b90847b3198b7feb Status: Downloaded newer image for my-aws-account.dkr.ecr.us-west-2.amazonaws.com/foo:latest
I can pull (and push if permitted) Docker images from the Amazon ECR without having to run thedocker login
command, and by implication, without having to install the AWS CLI solely for Docker login purposes.
I hope you find this information helpful. Please let me know if you find any inaccuracies and/or if you have any questions or comments.