First impressions of the fastest JavaScript runtime for Lambda Read on my blog Read time: 4 minutes I thought Lambda needed a specialised runtime. One that works well with its resource-constraint execution environment. I even floated a few ideas in the past but sadly I don’t have the chops to make them happen myself. So I was pleasantly surprised when AWS open-sourced the LLRT runtime for JavaScript [1]! What is LLRT?LLRT, or Low Latency Runtime, is a new and experimental JavaScript runtime for Lambda. It promises 10x faster startup time. Which should significantly help with the dreaded Lambda cold starts. Naturally, I had to test it out for myself and see if the hype was real. My first impressions of LLRTIn my limited tests, the Along the way, I also discovered several limitations:
LLRT is not ready for prime time yet. And given that it’s been in the works for almost two years, we should set expectations accordingly. It’s probably not going to be production-ready in the coming months. But the potential is there and I’m really excited about it! For one thing, it might finally stop people talking about cold starts. As I said on LinkedIn [5] yesterday, most people are overthinking about Lambda cold starts. If you’re not sure if Lambda cold starts is likely a problem for you, then go read the LinkedIn post and come back here. Back to LLRT. I later spoke with Richard Davison, the creator of the LLRT project. I wanted to learn more about the project and the design decisions behind it. What made it start so much faster? What trade-offs did they make? LLRT is the answer to the question “What would a purposely built JavaScript runtime look like for Lambda.” A lot of people see that “It’s built in Rust” and automatically assume that’s why it’s fast. But it’s more than that. When it comes to performance optimizations, it always boils down to what you let go. If you choose to do everything the incumbent does, then you won’t make any significant performance gains. No JIT compilationWith LLRT, they chose to not include a JIT compiler. Because it’s focused on Lambda’s resource constraint and short-lived execution environments. As a result, LLRT is likely less performant than the Node.js runtime for CPU-intensive tasks. However, most Lambda functions do not perform CPU-intensive tasks. Instead, they tend to be IO-intensive. And the Lambda execution environments are short-lived. So a JIT compiler would have been less effective at optimizing hot code paths. At the same time, a JIT compiler comes with significant startup costs. It also introduces occasional latency spikes when it needs to evict cached items. So it appears a sensible trade-off for LLRT to not include a JIT compiler. QuickJs + RustThe QuickJs engine [6] plays a crucial role in LLRT and its outstanding performance. Another reason why LLRT is fast is because they wrote all the APIs in Rust. As much as possible, the team wants to stay in native code to guarantee a strong performance. Bun [7] took the same approach and implemented all the APIs in a system language called Zig [8]. The downside to this approach is that it’s harder for contributors to get in on the action. There are a lot fewer Rust developers than Node.js developers. And even fewer Rust developers who are interested in a JavaScript runtime. LLRT vs Bun (and other JS runtimes)LLRT is different from other JavaScript runtimes. It’s not a general-purpose runtime for JavaScript. It doesn’t have to worry about running in the browser or on mobile phones. Instead, it’s solely focused on the Lambda execution environment. This allows them to make decisions that just wouldn’t make sense with Bun or Node.js. Decisions such as not including a JIT compiler. Or which of the JavaScript APIs do they implement first, or at all? The goal is to eventually become WinterCG compliant. But we don’t have to wait for that to start using LLRT. For LLRT to be useful (but not perfect!), it just needs to support the AWS SDK and a few popular libraries. SummaryTo summarize, LLRT is an exciting new runtime for JavaScript. It’s purposely built for Lambda. It’s not intended as a general-purpose runtime for JavaScript. It makes design trade-offs (such as not having a JIT compiler) to achieve an optimal cold start time. It uses the QuickJs engine and implements all the JavaScript APIs in Rust. To learn more about LLRT and how to contribute to it, please check out my conversation with Richard on YouTube [9]. I will be covering LLRT in my upcoming workshop, including how to use it with the Serverless Framework and CDK. If you wanna take your serverless game to the next level, then you should check it out! More information is available on the course page [10]. Links[1] GitHub repo for LLRT [3] LLRT’s API compatibility page [4] AWS Lambda Powertools for TypeScript [5] Most people are overthinking about Lambda cold starts [6] QuickJs engine [7] The Bun runtime for JavaScript [8] The Zip programming language [9] My interview with Richard Davison, the creator of LLRT [10] Production-Ready Serverless workshop Free workshop giveawayI'm giving away FREE seat(s) to my workshop in March. All you have to do is give me some feedback on my current landing page and leave your feedback in a comment here. Depending on the no. of comments, I will give away one or more seats. The winners will be picked at random on the 1st March. I'm good at this AWS and serverless thing, but not so much on UI and UX... So any help would be greatly appreciated! |
Join 13K readers and level up you AWS game with just 5 mins a week. Every Monday, I share practical tips, tutorials and best practices for building serverless architectures on AWS.
2024 was the year I got back and amongst the community, and it felt great to be back! Blog I published 33 new blog posts. As a whole, my blog garnered 353k views from 255k visitors. About half of them came through Google search. This is down from 2023... but the decline is offset by more people reading my content through my newsletter nowadays. Most read blog posts: Hit the 6MB Lambda payload limit? Here’s what you can do When to use Step Functions vs. doing it all in a Lambda function How to...
One of my favourite questions from the November cohort of Production-Ready Serverless [1] is, "How do you handle e2e tests involving multiple services across bounded contexts?" In a microservices environment, testing user journeys that span across multiple bounded contexts requires collaboration and a clear delineation of responsibilities. Depending on how your organisation is structured, different teams are responsible for testing parts or the entirety of the user journey. For example... The...
The ability to invalidate a user's session with immediate effect is a common enterprise requirement. For example: If a user's credentials are compromised, we need to immediately revoke the user's access and force the user to change credentials. If an employee is terminated or an external contractor's access is revoked, their session should be invalidated immediately to prevent misuse. Many regulations mandate strict access controls and the ability to prevent unauthorized access in real time....