Local Development and Testing of AWS services using LocalStack

In this post we explore how to test AWS services on our local machine without connecting to AWS.

Swati Maruvada


What problem are we trying to solve?

The Use Case

Lambda functions were being tested on the AWS console manually at our client site. We were looking for a way to test them locally so that it could be included in the CI/CD pipeline.


What is LocalStack?

Localstack is an open source tool that eliminates the cost of running AWS services by providing a test framework for developing AWS applications. By spinning up a testing environment on your local machine, it delivers the same functionality and APIs as the real AWS cloud environment. It is based on the existing set of tools like kinesalite/dynalite and moto and adds more functionality on top.

In order to run the AWS commands in LocalStack, another open source utility awscli-local needs to be installed which will emulate awscli commands.

The official Github repository of LocalStack is - https://github.com/localstack/localstack. Visit this page to understand the all the AWS services that are supported by LocalStack.


How will LocalStack help me?

We were able to solve the above mentioned problem by installing LocalStack on our local machine and writing Lambda functions along with the test cases and testing them (using LocalStack and awscli-local). LocalStack can also be integrated with any of the CI/CD pipelines as a part of the test step which will give us confidence that what we put on AWS will run without issues.

LocalStack also helps eliminate the cost associated with using the AWS services by emulating the services on their local machine (awscli-local works in the same way as the awscli). Both of these tools combined are a very powerful way of developing and testing the AWS services on your local machine without incurring any cost.


Let’s do it!


Pre-Requisites

  • MacOS or Linux system
  • make
  • python (both Python 2.x and 3.x supported)
  • pip (python package manager)
  • npm (node.js package manager)
  • java/javac (Java 8 runtime environment and compiler)
  • mvn (Maven, the build system for Java)
  • docker


Installation

The easiest way to install LocalStack is through docker-compose which uses the official LocalStack image that has all the base software requirements built in.

Installation steps:

1) Clone the GIT repository for LocalStack on your local machine and install docker compose. Ensure docker is installed and running

sudo yum install git

git clone[https://github.com/localstack/localstack.git](https://github.com/localstack/localstack.git "https://github.com/localstack/localstack.git")

sudo curl -L[https://github.com/docker/compose/releases/download/1.22.0/docker-compose-](https://github.com/docker/compose/releases/download/1.22.0/docker-compose- "https://github.com/docker/compose/releases/download/1.22.0/docker-compose-")$(uname -s)-$(uname -m) -o /usr/local/bin/docker-compose

sudo chmod +x /usr/local/bin/docker-compose

2) LocalStack uses custom ports defined in their LocalStack documentation. Ensure that these ports are not being used by any other services in your local machine. Start LocalStack in the background using docker-compose . Once LocalStack is started, use Ctrl+C to quit anytime.

docker-compose up &

3) Get the network name for LocalStack to which awslocal or other containers can connect. It will most likely be the name localstack_default.

docker network ls

4) Create a dockerfile for awscli-local with the below steps:

FROM amazonlinux

ENV AWS_DEFAULT_REGION ap-southeast-2

WORKDIR /home/ec2-user/LambdaDock

RUN yum install python-pip -y

RUN pip install awscli-local

5) Build the awslocal image and tag it with any name

docker build -f dockerfile -t awslocal.


Testing with LocalStack

1) Create the awslocal container using the image.

docker run -v /home/ec2-user --network=localstack_default -it <awslocal image ld>

2) Start the awslocal container

docker exec -i -t <awslocal image ld> bash

3) Once the container is running, any aws command can be run in the same way as working with awscli. The syntax of awslocal is same as awscli.

awslocal --endpoint-url=http://localstack_localstack_1:4574 lambda list-functions


Note:

  • localstack_localstack_1 is the NAMES field of the LocalStack container after running docker ps.
  • If the LocalStack setup is done on an EC2 instance, ensure that the LocalStack ports on which the AWS services are hosted are allowed in the security groups.