AWS API Gateway Multi-Stage Deployment with Lambda Alias

Mithun Das
Nov 28, 2018 · 4 min read

The Cloud Computing World is moving to Serverless architecture for obvious reasons. There is no need to keep your servers running and paying for 24X7 where you application may be serving your customers 50% of a day. You should pay only for the time your application actually processing your customer’s requests.

When we talk about Serveless Architecture on AWS, the very first thing would come to your mind is Apigateway with Lambda ! You can build your REST APIs without running EC2 instances. That’s very cool. But when I first adopted this stack, I was wondering how I can handle my CI/CD. For example, during development phase I like to update my lambda functions several times without effecting my PROD REST APIs which are being used by my customers. I deployed two Apigateway stages — dev and prod but problem was they both point to same lambda function. As a result, when I was updating my lambda function during development, it was effecting prod APIs as well.

Coming from Elastic Beanstalk where I can create multiple environments for an application and controlling code promotion from DEV to PROD so that PROD APIs are updated only when I decide to promote code from DEV to PROD, I was looking for similar mechanism using Apigateway and Lambda where I can control when to publish lambda code to PROD.

After some research I found we can achieve same behavior using Lambda alias with versioning and Apigateway stage variables.

When you use versioning in AWS Lambda, you can publish one or more versions of your Lambda function. As a result, you can work with different variations of your Lambda function in your development workflow. Each version is immutable with unique ARN. In addition, you can create aliases for your lambda function pointing to different immutable version. You can think alias as logical name of you environment specific lambda function which underneath points to different versions. For more information on this topic read this.

Now instead of directly assigning a lambda function in Apigateway integration request, you can assign lambda alias where alias is a variable. The variable will be resolved from a value from stage variable. For example you configure lambda function in Apigateway as myLamnda:${stageVariables.lambdaAlias} and define lambdaAlias stage variable in each of your Apigateway stages.

With above configurations, when you hit APIs from prod stage ( say /prod/todos), Apigateway will send the request to myLambda:PROD alias for fulfillment. myLambda:PROD points to immutable version. In your development environment (say /dev/todos) Apigateway (stage=dev) will point to myLambda:DEV alias which points to $LATEST version of your lambda function. As a result when you update code for your lambda function, it will update $LATEST version and immediately you can test your API in dev stage of Apigateway (/dev/todos). But it will not impact your prod API as it points to myLambda;PROD alias which behind the scene points to a immutable version.

Now when time comes to promote your lambda code to production, you create a version of you lambda code (from $LATEST) and update PROD alias to point to new version. That’s it !

One important note — when you are using lambda aliases, you need to grant permission to Apigateway for each aliases.

If you are interested in giving it a try by yourself, I wrote some terraform scripts to help you get started. All the AWS resources you need for this exercise such as lambda function, IAM role, aliases, api gatway resources, states will be created for you just by executing terraform commands from your terminal. Visit my github repo here for detail instructions.

Welcome to a place where words matter. On Medium, smart voices and original ideas take center stage - with no ads in sight. Watch
Follow all the topics you care about, and we’ll deliver the best stories for you to your homepage and inbox. Explore
Get unlimited access to the best stories on Medium — and support writers while you’re at it. Just $5/month. Upgrade