Location via proxy:   [ UP ]  
[Report a bug]   [Manage cookies]                

DEV Community

Vadym Kazulkin for AWS Heroes

Posted on

Spring Boot 3.4 application on AWS Lambda- Part 8 Optimization strategies for the cold and warm starts

Introduction

In the previous articles of the series about how to develop, run and optimize Spring Boot 3 application on AWS Lambda with :

  • AWS Serverless Java Container
  • AWS Lambda Web Adapter
  • Spring Cloud Function (and its AWS Adapter)
  • Deployed as a Lambda Docker Container Image
  • Based on GraalVM Native Image deployed as Lambda Custom Runtime

We also did Lambda performance (cold and warm starts) measurements with the following settings:

  • Lambda functions used 1024 MB memory
  • Java compilation option "-XX:+TieredCompilation -XX:TieredStopAtLevel=1" and the default tiered compilation have been used for the managed Java Lambda runtime and Lambda Docker Container Image
  • Lambda x86_64 architecture was used
  • Default Apache HTTP Client was used to connect to the DynamoDB

In this part of the series we'll introduce some Lambda additional performance (cold and warm starts) optimization techniques that you can apply for your Spring Boot 3 application on AWS Lambda. You'll need to measure the performance by yourself to figure out whether they will provide desired Lambda performance improvements.

Optimization strategies for the cold and warm starts

To find a good balance between cold and warm start times you can try out the optimization techniques introduced below. I have not done any measurements with the Spring Boot 3 application on AWS Lambda, but have done them using pure Java on AWS Lambda without the usage of any frameworks on top. I'll provide references to my relevant articles.

The following approaches can be applied to all approaches: managed Java runtime on Lambda including enabling SnapStart (and priming techniques on top), Lambda Docker Container Image and GraalVM Native Image deployed as Lambda Custom Runtime:

The following approaches can be applied primary to the managed Java runtime on Lambda including enabling SnapStart (and priming techniques on top) and Lambda Docker Container Image :

  • Try out different Java compilation options for the Lambda function. All measurements until now have been performed with the compilation option "-XX:+TieredCompilation -XX:TieredStopAtLevel=1" and default tiered compilation for the Lambda function. There are other compilation options that can be provided to the Lambda function using environment variable called JAVA_TOOL_OPTIONS which can have different cold and warm starts trade offs. See my article Measuring cold and warm starts with Java 21 using different compilation options for further examples, performance measurements and conclusions. In case of GraalVM Native Image Java compilation method (and optimizations during runtime) doesn't have much impact on the Lambda performance (well, because it's already compiled as a native image).
  • Further exclude unused dependencies. With that especially cold start times can be reduced (also for SnapStart), see my article Measuring cold starts with Java 21 using different deployment artifact sizes. In case of GraalVM Native Image only reachable Java classes, function and methods will become a part of the Native Image, so including unsued dependencies may not hear that much.

The following approach can be applied can be applied primary to the managed Java runtime on Lambda with enabled SnapStart:

The following approach can be applied primary to the GraalVM Native Image :

  • Try out Profile-Guided Optimizations to see whether you can further improve Lambda performance. The difficulty of trying out this technique is that you'll need to do some additional semi-automated steps to run your application either with the Lambda emulator locally or on the extra environment to obtain the profile of your application which you'll then need to generate the optimized Native Image. You can use Lambda extension for it, but it still requires a lot of additional work. The same work is done by AWS for us in case Lambda SnapStart is activated and I really appreciate that I don't need to care about generating, encrypting, storing and restoring the snapshots/profiles.

Conclusion

In this part of the series, we introduced some additional Lambda performance (cold and warm start times) optimization strategies to be used for the Spring Boot 3 application on AWS Lambda. Try them out on your own to figure out whether they will provide desired Lambda performance improvements.

Top comments (0)