Serverless application with AWS Lambda and Kotlin. Part 3

Volodymyr Sulevskyi
Coinmonks
4 min readAug 18, 2018

--

Part 3— Improving performance: Kotlin + Node.js+ AWS Lambda

This series of articles consists of 4 parts:

  1. Intro to Serverless applications and Functions-as-a-Service
  2. First blood: Writing functions in Kotlin for Java platform on AWS Lambda
  3. Warmup optimization: Writing functions in Kotlin for Node.js platform on AWS Lambda (you are here)
  4. Using familiar tools: Writing functions in Kotlin for for Java platform using Spring Cloud Functions on AWS Lambda

Purpose of this part of series is to show how to create a function on AWS Lambda based on Node.js platform with Kotlin programming language.

In previous chapter we’ve deployed a simple serverless application based on Java platform using Kotlin programming language. The issue was a so called cold start — when first function invocation takes long time — in our case 8 seconds instead of 300 ms in later invocations.

One of the solution recommended in the tech blogs to address this issue is to use dynamic typed languages (Python, JavaScript) instead of statically typed. But we still want to use Kotlin and it’s cool features. And actually type checking provided by Kotlin during development helps a lot.

There is a possibility to compile Kotlin code to JavaScript. With KotlinJS we will try to make startup faster.

The idea of application is the same as in previous article — to receive data from the API Gateway and to store it to S3 bucket. We still want an deployment configured in Gradle.

All source code can be downloaded from Github.

  1. Setup the project

In Java example we’ve built a fat jar to include all runtime dependencies to deployable artifact. In this example we will go similar way and create deployable artifact (zip archive) with JS libraries included.

To setup gradle compilation to JS step we need to include kotlin2js gradle plugin, it adds gradle tasks compileKotlin2Js, compileTestKotlin2Js. Configuration is quite simple.

Installing dependencies is important part in project setup. First we need to include kotlin-stdlib-js dependency which provides standard Kotlin features in JS environment.

Second we need to provide JS runtime dependencies. In package.json we specify them.

And in gradle script we will create a task to install dependencies (requires com.moowork.node plugin).

Packaging is made with zip task from gradle and deployment with aws-gradle plugin.

2. Lambda Code

Our intention to preserve code with business logic most similar to the code in implementation for Java platform to make transition from Java to Node.js as seamless as possible. It requires encapsulation of interaction of Kotlin Code and JS. Task may become difficult when there are many libraries, but in our case it’s only AWS S3 SDK and small number of standard JS functions (require and process.env). In other aspects switching to KotlinJS won’t be so difficult for Java/Kotlin developers.

Calls to JS functions encapsulated in specific module, business logic should not be couples with platform specific functions.

Important note: I do not say that transfer from Kotlin to KotlinJS will be seamless, you have learn KotlinJS specific concepts like dynamic types, external modifier, kotlin-js standard library, etc.

To implement function we have to create function which receives request object, context and callback parameters and mark it with annotation @JsName to make available for import.

AWS Lambda requires specification of entrypoint to the function. Let’s create simple JS file and specify entrypoint.

That’s it we’ve setup a project which can import JS dependencies, build and deploy function to AWS.

For development it is also good to have testing features set up.

3. Testing

JetBrains provides a library org.jetbrains.kotlin:kotlin-test-js for testing in KotlinJS. As you can see in an example test are very similar to JUnit tests which again simplifies development for Java/Kotlin developers.

Sample test with kotlin-test-js

For testing we need to properly setup compilation, packaging and running test framework (Jasmin in our example).

Testing tasks

We’ve setup an environment ready for development, testing and deployment.

Some performance metrics

Function duration on Node.js comparing to Java platform

As you can see in our measurements function running on Node.js platform has much less start time comparing to Java platform. But this improvement comes with a price — for Java/Kotlin developer writing code in Kotlin and compile to JS requires some knowledge of the platform.

Summary:

  1. With this example we have ready for development pipeline and with single commandgradle deployFunction full build/test/deploy lifecycle is covered
  2. Transition from Java to Node.js platform shouldn’t take much efforts due to encapsulation of JS code
  3. Out measurements show smaller warmup time on Node.js comparing to Java platform with small changes in code responsible for business logic written in Kotlin in both examples

Get Best Software Deals Directly In Your Inbox

--

--