-
Notifications
You must be signed in to change notification settings - Fork 48
Description
A few weeks ago AWS announced SnapStart, a feature to improve cold-start performance for JVM Lambdas. A few lines of config to make my Lambdas magically faster? Yes please!
With SnapStart, Lambda initializes your function when you publish a function version. Lambda takes a Firecracker microVM snapshot of the memory and disk state of the initialized execution environment, encrypts the snapshot, and caches it for low-latency access. When you invoke the function version for the first time, and as the invocations scale up, Lambda resumes new execution environments from the cached snapshot instead of initializing them from scratch, improving startup latency.
My understanding of that paragraph is that they will "initialize" by calling the constructor on the handler class, but they won't invoke the Lambda, i.e. call the handler method.
Unfortunately (if I'm understanding Feral's code correctly) it appears that Feral Lambdas won't benefit much from this optimization. As I understand it, Feral does pretty much nothing at class initialization time. The resource defined in def init
is acquired the first time the Lambda is invoked, and then memoized for reuse by subsequent invocations. So the SnapStart snapshot will capture the JVM startup and a bit of classloading, but none of the work performed while acquiring the init
resource.
It would be nice if we could make everything that happens in IOSetup
happen eagerly at class init time to take full advantage of SnapStart.
For now we can emulate this in user-land by eschewing def init
and just doing a good old unsafeRunSync
:
class MyLambda extends IOLambda.Simple[KinesisStreamEvent, INothing]:
type Init = Unit
private def buildAlgebra: IO[MyAlgebra[IO]] = ??? // the stuff that would usually go in `def init`
private val algebra: MyAlgebra[IO] = buildAlgebra[IO].unsafeRunSync()
override def apply(
event: KinesisStreamEvent,
context: Context[IO],
init: Init
): IO[Option[INothing]] = algebra.process(event, context)
Disclaimer: I haven't done any benchmarking with SnapStart and Feral yet.