aws / aws-lambda-dotnet

Libraries, samples and tools to help .NET Core developers develop AWS Lambda functions.
Apache License 2.0
1.58k stars 477 forks source link

GenerateMain=true results in Runtime Exception #1847

Closed Niaxor closed 1 month ago

Niaxor commented 1 month ago

Describe the bug

I'm testing dotnet 8 Lambda w/ Native AOT, and when using GenerateMain=true it results in a Runtime Exception with no further details when executed. This is reproduce-able with a modified version of the NativeAOTSample.

Regression Issue

Expected Behavior

Modifying the NativeAOTSample with GenerateMain=true, then deploying the lambda should function normally, and return the ToUpper() result.

Current Behavior

When running the lambda function in a docker container -

Sending a post request to this will result in a 502 bad gateway, and the following output in the console for the docker container:

24 Oct 2024 09:18:09,387 [INFO] (rapid) exec '/var/runtime/bootstrap' (cwd=/var/task, handler=) 24 Oct 2024 09:18:09,388 [DEBUG] (rapid) Runtime API Server listening on 127.0.0.1:9001 24 Oct 2024 09:18:12,309 [DEBUG] (rapid) invoke: -> POST /2015-03-31/functions/function/invocations map[Accept:[/] Accept-Encoding:[gzip, deflate, br] Cache-Control:[no-cache] Connection:[keep-alive] Content-Length:[7] Content-Type:[text/plain] Postman-Token:[544c6bf8-7341-4436-a898-678a82c6ac8b] User-Agent:[PostmanRuntime/7.42.0]] START RequestId: 0b727f17-5a77-43e2-9f84-ba3559d5e5d8 Version: $LATEST 24 Oct 2024 09:18:12,310 [INFO] (rapid) INIT START(type: on-demand, phase: init) 24 Oct 2024 09:18:12,310 [INFO] (rapid) The extension's directory "/opt/extensions" does not exist, assuming no extensions to be loaded. 24 Oct 2024 09:18:12,310 [DEBUG] (rapid) Preregister runtime 24 Oct 2024 09:18:12,313 [DEBUG] (rapid) Start runtime 24 Oct 2024 09:18:12,313 [INFO] (rapid) Starting runtime without AWS_ACCESS_KEY_ID, AWS_SECRET_ACCESS_KEY, AWS_SESSION_TOKEN , Expected?: false 24 Oct 2024 09:18:12,441 [DEBUG] (rapid) The events handler received the event {Time:1729761492441 Event:{EvType: Domain:0xc0000e0010 Name:0xc0000e0000 Cause: Signo: ExitStatus:0xc0001820fc Size:}}. 24 Oct 2024 09:18:12,441 [WARNING] (rapid) First fatal error stored in appctx: Runtime.ExitError 24 Oct 2024 09:18:12,441 [WARNING] (rapid) Process runtime-1 exited: exit status 0 24 Oct 2024 09:18:12,441 [DEBUG] (rapid) Canceling flows: Runtime exited without providing a reason 24 Oct 2024 09:18:12,441 [INFO] (rapid) INIT RTDONE(status: error) 24 Oct 2024 09:18:12,441 [INFO] (rapid) INIT REPORT(durationMs: 131.026000) 24 Oct 2024 09:18:12,441 [ERROR] (rapid) Init failed error=Runtime exited without providing a reason InvokeID= 24 Oct 2024 09:18:12,441 [WARNING] (rapid) Shutdown initiated: spindown 24 Oct 2024 09:18:12,441 [DEBUG] (rapid) SIGKILLing the runtime as no agents are registered. 24 Oct 2024 09:18:12,441 [DEBUG] (rapid) Process runtime-1 already terminated. 24 Oct 2024 09:18:12,441 [INFO] (rapid) Waiting for runtime domain processes termination 24 Oct 2024 09:18:12,441 [INFO] (rapid) INIT START(type: on-demand, phase: invoke) 24 Oct 2024 09:18:12,441 [INFO] (rapid) The extension's directory "/opt/extensions" does not exist, assuming no extensions to be loaded. 24 Oct 2024 09:18:12,441 [INFO] (rapid) INIT REPORT(durationMs: 0.030000) 24 Oct 2024 09:18:12,441 [INFO] (rapid) INVOKE START(requestId: 32cb2b34-616d-42ca-b942-9069ff4f39f6) 24 Oct 2024 09:18:12,441 [ERROR] (rapid) Invoke failed error=Runtime exited without providing a reason InvokeID=32cb2b34-616d-42ca-b942-9069ff4f39f6 24 Oct 2024 09:18:12,441 [DEBUG] (rapid) Sending Error Response: Runtime.ExitError 24 Oct 2024 09:18:12,441 [ERROR] (rapid) Invoke DONE failed: Sandbox.Failure 24 Oct 2024 09:18:12,441 [DEBUG] (rapid) AwaitRelease() error: InvokeDoneFailed 24 Oct 2024 09:18:12,441 [WARNING] (rapid) Reset initiated: ReleaseFail 24 Oct 2024 09:18:12,441 [DEBUG] (rapid) Could not find runtime process runtime-2 in processes map. Already exited/never started 24 Oct 2024 09:18:12,441 [INFO] (rapid) Waiting for runtime domain processes termination 24 Oct 2024 09:18:12,441 [DEBUG] (rapid) Invoke() release error 24 Oct 2024 09:18:12,441 [DEBUG] (rapid) execute finished, autoreset cancelled

Reproduction Steps

To reproduce, I have modified the NativeAotSample supplied by AWS to use automatic main generation.

using Amazon.Lambda.Annotations;
using Amazon.Lambda.Core;
using Amazon.Lambda.RuntimeSupport;
using Amazon.Lambda.Serialization.SystemTextJson;
using NativeAOTSample;
using System.Text.Json.Serialization;

[assembly: LambdaGlobalProperties(GenerateMain = true)]
[assembly: LambdaSerializer(typeof(SourceGeneratorLambdaJsonSerializer<LambdaFunctionJsonSerializerContext>))]
namespace NativeAOTSample;

[LambdaStartup]
public class Function
{
    [LambdaFunction]
    public string FunctionHandler(string input, ILambdaContext context)
    {
        return input.ToUpper();
    }
}

[JsonSerializable(typeof(string))]
public partial class LambdaFunctionJsonSerializerContext : JsonSerializerContext
{
}

dotnet lambda package will succeed in generating native code without error from this.

Then running in a docker container -

docker run --rm -it -e LOG_LEVEL='trace' -v ${pwd}/bin/Release/net8.0/publish:/var/task -p 9000:8080 amazon/aws-lambda-dotnet:8 NativeAOTSample

Possible Solution

No response

Additional Information/Context

Using a static FunctionHandler does not seem to be compatible with GenerateMain=true as it then generates code that doesn't compile. It's not clear if this is intended behaviour or not as it is not a handled error.

... docker run: /tmp/source/NativeAOTSample/src/NativeAOTSample/obj/Release/net8.0/linux-x64/Amazon.Lambda.Annotations.SourceGenerator/Amazon.Lambda.Annotations.SourceGenerator.Generator/Function_FunctionHandler_Generated.g.cs(38,20): error CS0176: Member 'Function.FunctionHandler(string, ILambdaContext)' cannot be accessed with an instance reference; qualify it with a type name instead [/tmp/source/NativeAOTSample/src/NativeAOTSample/NativeAOTSample.csproj]

Using an explicit Main function, without GenerateMain=true as per the original sample works fine I.e.

    private static async Task Main()
    {
        Func<string, ILambdaContext, SampleType> handler = FunctionHandler;
        await LambdaBootstrapBuilder.Create(handler, new SourceGeneratorLambdaJsonSerializer<LambdaFunctionJsonSerializerContext>())
            .Build()
            .RunAsync();
    }

AWS .NET SDK and/or Package version used

Amazon.Lambda.Annotations (1.5.2) Amazon.Lambda.Core (2.2.0) Amazon.Lambda.RuntimeSupport (1.10.0) Amazon.Lambda.Serialization.SystemTextJson (2.4.1)

Targeted .NET Platform

.NET 8

Operating System and version

Windows 10 + AmazonLinux

Niaxor commented 1 month ago

The issue was that I wasn't setting the ANNOTATIONS_HANDLER environment variable when testing with docker, after reviewing the generated Program.cs I realised that this is a runtime requirement else the program will just literally immediately exit with no error.

github-actions[bot] commented 1 month ago

Comments on closed issues are hard for our team to see. If you need more assistance, please either tag a team member or open a new issue that references this one. If you wish to keep having a conversation with other community members under this issue feel free to do so.