My journey with AWS Serverless. Tips and lesson learned about AWS…

By Miron Machnicki

The tricky part is to proper organise architecture — split logic into multiple functions and transfer data between them. That splitting makes sense especially if one part of logic is invoked more often than other, or if one part is more complicated, takes more time / memory to compute. Another reason could be, that for one function you would like to have concurrency limit— for example to avoid too many requests to external API or DB (throttling issues).

Know the difference between sync and async Lambda

You can invoke Lambda synchronously or asynchronously. If your logic is simple and you expect direct response from your function, invoke Lambda synchronously (InvocationType = RequestResponse). For example Lambda calls via API Gateway or Elastic Load Balancer are synchronous, as you expect response.

Image for post
Image for post
Within AWS Step Functions you can orchestrate event driven application // source: AWS
Image for post
Image for post
On failure destination gives a bit more option than dead-letter queue // source: AWS

Think about multiple ways of triggering Lambda

You can trigger Lambdas by events emitted from different sources. List of possible event sources is long.

Image for post
Image for post
Apart from AWS services you can integrate your lambda with partners event sources (via EventBridge) // source: AWS
  • SQS — queues (pull) are ideal solution when you expect throttling problem — for example if your traffic is very dynamic and you would like to avoid to lose any messages, or if you want to optimize Lambda autoscaling (60 additional instances per minute to a maximum of 1,000 concurrent invocations);
  • EventBridge (CloudWatch Events) — used for more complex events management, where you can filter by event patterns, subscribe to scheduled job (cron), 3rd party emitters and more — such as communication between accounts;
  • Kinesis — dedicated for streaming or data driven applications;
  • S3 — you can trigger Lambda based on changes in S3 bucket eg. one service upload file, other service does some operation on it;
  • DynamoDB — Lambda can read records from DB stream, so you can react each time, when data changes;
Image for post
Image for post
Cheatsheet for choosing async event sources for Lambda // source: @theburningmonk

Get some inspirations from others

There are many different ways to deal with events in AWS, so I encourage you to read about how others build theirs async architecture. Great source of patterns and solutions is AWS Solutions Reference Architectures and cdkpatterns.com.

Image for post
Image for post
The Big Fan is a popular pattern based on SNS and SQS (filtering to fan out events to different consumers) // source: cdkpatterns.com

Understand Lambda execution to improve speed

When you are Node.js developer, cold starts (increased invocation latency) might not be your main issue. If Lambda does a lot of work eg. soon after invocation (making connection to DB, retrieving data from SSM or so), you might want to improve that speed — especially if that could improve UX.

Image for post
Image for post
The lifecycle of the execution environment — there could be many invocations within the same runtime, so you might cache some data in global Node.js scope // source: AWS

Use Lambda layers

You might be in situation, that one service share a lot of code with others. In Node.js you can have some common node_modules and it might not be good idea to include all of them in each bundle, or to deploy to each Lambda container separately. Think about deploy common code as AWS Lambda layer. It could be useful also if some part of your Lambdas code is heavy, and you would like to avoid deploying it each time, when you change something.