DEV Community

Mark Davies
Mark Davies

Posted on

Using localstack to run an API

What is localstack?

GitHub logo localstack / localstack

πŸ’» A fully functional local AWS cloud stack. Develop and test your cloud & Serverless apps offline!

Build Status Backers on Open Collective Sponsors on Open Collective Coverage Status Gitter PyPI Version PyPI License Code Climate Twitter

LocalStack - A fully functional local AWS cloud stack

LocalStack

LocalStack provides an easy-to-use test/mocking framework for developing Cloud applications.

Currently, the focus is primarily on supporting the AWS cloud stack.

Announcements

  • 2020-12-28: Check out the LocalStack Pro feature roadmap here: https://roadmap.localstack.cloud - please help us prioritize our backlog by creating and upvoting feature requests. Looking forward to getting your feedback!
  • 2020-09-15: A major (breaking) change has been merged in PR #2905 - starting with releases after v0.11.5, all services are now exposed via the edge service (port 4566) only! Please update your client configurations to use this new endpoint.
  • 2019-10-09: LocalStack Pro is out! We're incredibly excited to announce the launch of LocalStack Pro - the enterprise version of LocalStack with additional APIs and advanced features. Check out the free trial at https://localstack.cloud
  • 2018-01-10: Help wanted! Please fill out this survey to support a research…

Let's start at the beginning - what is localstack exactly?

Localstack an open source project that provides users with api's that fulfil the api's provided by the amazon web services, what does this mean? It means that you can have your own AWS running on your own - local - machine.

What are the advantages of this?

There are a few reason why you might use localstack, let's quickly list them πŸ˜„

πŸ’°πŸ’° Price πŸ’°πŸ’°

Sometimes spinning up test resources in AWS is expensive, especially if you are an individual (or maybe a corporation with a a lot of individual employees) spinning up a for example dynamo db table for each developer to develop against would probably be more expensive than any service you want to create.

The base version of localstack (that includes dynamo service) is free! So in a development environment you could have people communicate with that service.

πŸƒβ€β™€οΈπŸƒβ€β™‚οΈ Speed πŸƒβ€β™€οΈπŸƒβ€β™‚οΈ

Sometimes communicating with the cloud can be expensive not for the pocket but for wait times, this way all tests and code will be talking to a local version so should be faster πŸ˜‰.

I don't know about you but I work at a company that has a devops team that like to be "in charge" of all of the infrastructure - which means that if I need a new S3 bukcet, dynamo database, or (insert other services here) I have to raise a ticket to create a piece of insfrastructure for testing, which can take time. With a local version of AWS I can spin up whatever I want, so whilst I wait for actual infrastructure I can continue with my work locally.

🎀🎀 Testing 🎀🎀

We can create tests against the local version, which means if we've broken anything we can run the same tests as we did for the previous version and if any fail we know that something has been broken whilst developing the new feature faster.

πŸ“•πŸ“–πŸ“‘ How do we use it? πŸ“•πŸ“–πŸ“‘

There are a few ways to "use" localstack, one of my favourite ways is to have a docker compose file (just to note I will not be talking about docker here) which look something like this:

version: '3.4'

services:
  my.localstack:
    image: localstack/localstack:latest
    container_name: my-localstack
    ports:
      - "4566:4566"
    environment:
      - DEFAULT_REGION=eu-west-1
      - DATA_DIR=/tmp/localstack/data
    volumes:
      - "./setup-dev-env.sh:/docker-entrypoint-initaws.d/setup-dev-env.sh"
      - "./local/creds.json:/docker-entrypoint-initaws.d/creds.json"
Enter fullscreen mode Exit fullscreen mode

Working with Localstack

One of the things that I wanted to achieve with Localstack was to create a test infrastucture with a legacy application I've been working on. This particular API made use of the following AWS features:

  • Dynamo DB
  • S3
  • SQS

Attempting to make it as simple as possible for developers to clone the code from our private repository and hit build and have a localstack instance running on their machine in a configuration that would allow them to perform every branch of code in the API.

Running Localstack

We work with c# dotnet - our editor of choice is visual studio (my personal editor of choice is Rider), dotnet provides two event hooks to run anything that you may want to run before the build completes, this is where I added a call to powershell:

powershell.exe -ExecutionPolicy Bypass -NoProfile -NonInteractive -File $(SolutionDir)setup-dev-env.ps1 $(SolutionDir)
Enter fullscreen mode Exit fullscreen mode

Just as a note of where this is in Visual studio if you right click your project and click "properties" and go to build events, this particular script is entered intot he "pre-build event command line"

This script checks to see if a particular docker container has been created - if not then it will call the docker-compose file within the direction that is passed into the script (the solution directory):

param($dir)

$isLocalStackRunning = docker container ps -f Name=localstack -q

if([string]::IsNullOrEmpty($isLocalStackRunning))
{
    docker-compose --file $dir\docker-compose.yml up -d
}
Enter fullscreen mode Exit fullscreen mode

just as a reference:

Flag What this does
-f Filters the results
-q "Quiet" mode (just returns the docker container id)

full reference for this command here

The docker file:

version: '3.4'

services:
  my.localstack:
    image: localstack/localstack:latest
    container_name: localstack
    ports:
      - "4566:4566"
    environment:
      - DEFAULT_REGION=eu-west-1
      - DATA_DIR=/tmp/localstack/data
    volumes:
      - "./setup-dev-env.sh:/docker-entrypoint-initaws.d/setup-dev-env.sh"
      - "./local/creds.json:/docker-entrypoint-initaws.d/creds.json"
Enter fullscreen mode Exit fullscreen mode

Infrastructure

You may have noticed this line in my docker-compose file: "./setup-dev-env.sh:/docker-entrypoint-initaws.d/setup-dev-env.sh", this is essentially copying a file into directory inside the docker container, every .sh file in this particular directory of localstack gets run when we run the docker-compose up command, this is where I create all of the infrastructure that the API need to run:

awslocal dynamodb create-table --table-name Table1 --attribute-definitions AttributeName=KC,AttributeType=S AttributeName=Domain,AttributeType=S --key-schema AttributeName=KC,KeyType=HASH  AttributeName=Domain,KeyType=RANGE --provisioned-throughput ReadCapacityUnits=1000,WriteCapacityUnits=1000
awslocal dynamodb create-table --table-name table2 --attribute-definitions AttributeName=KC,AttributeType=S AttributeName=Domain,AttributeType=S --key-schema AttributeName=KC,KeyType=HASH  AttributeName=Domain,KeyType=RANGE --provisioned-throughput ReadCapacityUnits=1000,WriteCapacityUnits=1000
awslocal sqs create-queue --queue-name queue1
awslocal sqs create-queue --queue-name queue2.fifo --attributes "FifoQueue=true"
awslocal sqs create-queue --queue-name queue2failover.fifo --attributes "FifoQueue=true"
awslocal kinesis create-stream --stream-name stream1 --shard-count 1
awslocal s3 mb s3://bucket --region eu-west-1
awslocal s3 cp /docker-entrypoint-initaws.d/creds.json s3://bucket/SVC/apiauth/creds.json
Enter fullscreen mode Exit fullscreen mode

Note Because this files runs inside of the container keep in mind that it is a Linux exclusive container so this file will need the LF new line endings (yes this caught me out πŸ˜„)


Now when I build my solution it checks to see if I have my container running if I don't it will create it with all of the things I need to exercise the API πŸ˜„

Top comments (0)