aws-lambda-dotnet: Amazon.Lambda.TestTool-6.0 serialization exception on Lambda's return value when using JSON serializer source generators
Description
An exception is thrown when trying to convert the result object of the function handler back to a stream in the Mock Lambda Test Tool on .Net 6 when using JSON source generators to serialize the result object.
This happens with types T for both T and Task<T> result types of the function handler, such as APIGatewayHttpApiV2ProxyResponse and Task<APIGatewayHttpApiV2ProxyResponse>, respectively.
An example of an exception thrown when the function handler’s result type is APIGatewayHttpApiV2ProxyResponse:
Amazon.Lambda.Serialization.SystemTextJson.JsonSerializerException: Error converting the response object of type System.Object from the Lambda function to JSON: No JsonTypeInfo registered in AWSLambdaTest.HttpApiJsonSerializerContext for type System.Object.
Reproduction Steps
From Visual Studio 2022, run the AWS .NET Core 6.0 Mock Lambda Test Tool with the following example code (a failing case for a non-async function handler). In Test Function select example request API Gateway V2 HTTP API and click Execute Function.
using Amazon.Lambda.APIGatewayEvents;
using Amazon.Lambda.Core;
using Amazon.Lambda.Serialization.SystemTextJson;
using System.Text.Json.Serialization;
// Assembly attribute to enable the Lambda function's JSON input to be converted into a .NET class.
[assembly: LambdaSerializer(typeof(SourceGeneratorLambdaJsonSerializer<AWSLambdaTest.HttpApiJsonSerializerContext>))]
namespace AWSLambdaTest;
[JsonSerializable(typeof(APIGatewayHttpApiV2ProxyRequest))]
[JsonSerializable(typeof(APIGatewayHttpApiV2ProxyResponse))]
public partial class HttpApiJsonSerializerContext : JsonSerializerContext
{
}
public partial class Function
{
public APIGatewayHttpApiV2ProxyResponse Get(APIGatewayHttpApiV2ProxyRequest request, ILambdaContext context)
{
return new APIGatewayHttpApiV2ProxyResponse
{
Body = request.Body.ToUpper(),
StatusCode = 200
};
}
}
Expected response:
{"statusCode":200,"body":"HELLO FROM LAMBDA","isBase64Encoded":false}
Actual response:
Amazon.Lambda.Serialization.SystemTextJson.JsonSerializerException: Error converting the response object of type System.Object from the Lambda function to JSON: No JsonTypeInfo registered in AWSLambdaTest.HttpApiJsonSerializerContext for type System.Object.
at Amazon.Lambda.Serialization.SystemTextJson.AbstractLambdaJsonSerializer.Serialize[T](T response, Stream responseStream)
at Amazon.Lambda.TestTool.Runtime.LambdaExecutor.ProcessReturnAsync(ExecutionRequest request, Object lambdaReturnObject) in C:\codebuild\tmp\output\src581676283\src\Tools\LambdaTestTool\src\Amazon.Lambda.TestTool\Runtime\LambdaExecutor.cs:line 162
at Amazon.Lambda.TestTool.Runtime.LambdaExecutor.ExecuteAsync(ExecutionRequest request) in C:\codebuild\tmp\output\src581676283\src\Tools\LambdaTestTool\src\Amazon.Lambda.TestTool\Runtime\LambdaExecutor.cs:line 62
---------------- Inner 1 Exception ------------
Amazon.Lambda.Serialization.SystemTextJson.JsonSerializerException: No JsonTypeInfo registered in AWSLambdaTest.HttpApiJsonSerializerContext for type System.Object.
at Amazon.Lambda.Serialization.SystemTextJson.SourceGeneratorLambdaJsonSerializer`1.InternalSerialize[T](Utf8JsonWriter writer, T response)
at Amazon.Lambda.Serialization.SystemTextJson.AbstractLambdaJsonSerializer.Serialize[T](T response, Stream responseStream)
Logs
AWS .NET Core 6.0 Mock Lambda Test Tool (0.12.1)
Loaded local Lambda runtime from project output D:\src-test-2022\AWSLambdaTest\bin\Debug\net6.0
Found Lambda config file D:\src-test-2022\AWSLambdaTest\aws-lambda-tools-defaults.json
Environment running at http://localhost:5050
Environment
- Build Version: Amazon.Lambda.TestTool
0.12.1 - OS Info: Windows 10 Build
19044.1586 - Build Environment: Visual Studio 2022
Version 17.1.2 - Targeted .NET Platform: .Net 6 on Linux x64
Resolution
- 👋 I can/would-like-to implement a fix for this problem myself
- 👋 I think a have found a solution
It seems to be the case that the serialization implementation is trying to use a serializer supporting the static type of the result object (System.Object) in the Lambda TestTool (and not the dynamic/runtime type, like APIGatewayHttpApiV2ProxyResponse in the example above) to convert the result back to a stream (for which the source-generated serializer has no support).
A possible solution involves invoking the generic Serializer method with the correct runtime type as the type argument (instead of System.Object).
This is a 🐛 bug-report
About this issue
- Original URL
- State: closed
- Created 2 years ago
- Reactions: 1
- Comments: 15 (7 by maintainers)
@normj – ran an initial test and all seems good – thanks for the quick response and fix!
I just pushed out version
0.12.5with the fix.Reproducible using customer’s code. Needs review with the team.