aws-lambda-dotnet
aws-lambda-dotnet copied to clipboard
Support async function initialization with the .NET 6 managed runtime
Issue #1087
Description of changes:
Adds support for asynchronous initialization of classes that implement handlers for lambdas by introducing a new IHandlerInitializer
interface (the specific name is open for discussion).
If an instance-based class (i.e. not a static class) used for a handler implements the IHandlerInitializer
interface, it is invoked during the initialization of user code. If the method throws an exception or returns false
(the need to return a boolean is also open for discussion), then an exception is thrown and the Lambda runtime would report the initialization failure. Otherwise if the method returns true
, then the code is considered to be initialized and ready to process requests.
If the handler class is static or does not implement this interface, execution is the same as it is today.
Using the interface allows the user to opt-in to asynchronous initialization in an idiomatic way that integrates with the existing asynchronous initialization support for custom runtimes without the need to block on tasks in a class constructor.
By submitting this pull request, I confirm that my contribution is made under the terms of the Apache 2.0 license.
The challenge for this is a Lambda function using managed runtime doesn't have a direct dependency on Amazon.Lambda.RuntimeSupport
. The alternative would be to put IHandlerInitializer
in Amazon.Lambda.Core
but that also has problems because the user brings the version of Amazon.Lambda.Core
. If a user brings in an old version that doesn't have IHandlerInitializer
then Amazon.Lambda.RuntimeSupport
blows up with a missing type exception. That is why the new logging methods added for .NET 6 were added to the logger interface with a default implementation.
I think the safe way to add this is lookup the InitializeAsync
method by convention just like we look for the handler method instead of relying on an interface.
Another concern is we would be making one more reflection call during cold start, so we need to make sure that does not add any significant performance hit when there isn't a InitializeAsync
at the lowest memory setting.
Also the boolean seems unnecessary. If the task returned has a failed status we know initialization failed.
Thanks for the feedback Norm. I'll have a rethink on how to approach this.
I've changed this to remove the interface, and instead invoke a method with either of the following two signatures if found on the handler's type:
-
public static Task InitializeAsync()
-
public Task InitializeAsync()
There's a few open questions marked with // TODO
comments.
I'm going to close for lack of activity.
InitializeAsync would still be a nice shot ..