aws / aws-lambda-dotnet

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

Lambda Annotations doesn't support a function returning `Task<T[]>` for any `T` #1368

Closed Kralizek closed 1 year ago

Kralizek commented 1 year ago

Describe the bug

When trying to build a function written using the new Annotation framework that returns an array, the build fails

[LambdaFunction]
public async Task<Country[]> GetCountriesAsync([FromServices] IHttpClientFactory httpClientFactory, string name)
{ ... }

Expected Behavior

It should be possible to create a function that returns an array of items.

Current Behavior

$ dotnet build

MSBuild version 17.4.0+18d5aef85 for .NET
  Determining projects to restore...
  All projects are up-to-date for restore.
CSC : error AWSLambda0001: This is a bug. Please run the build with detailed verbosity (dotnet build --verbosity detailed) and file a bug at https://github.com/aws/aws-lambda-dotnet with the build output and stack trace Unable to cast object of type 'Microsoft.Code
Analysis.CSharp.Symbols.PublicModel.ArrayTypeSymbol' to type 'Microsoft.CodeAnalysis.INamedTypeSymbol'.   at Amazon.Lambda.Annotations.SourceGenerator.Models.TypeModelBuilder.Build(ITypeSymbol symbol, GeneratorExecutionContext context) [C:\Users\RenatoGolia\Develop 
ment\Labs\FindNationalityFunction\FindNationalityFunction.csproj]

Build FAILED.

CSC : error AWSLambda0001: This is a bug. Please run the build with detailed verbosity (dotnet build --verbosity detailed) and file a bug at https://github.com/aws/aws-lambda-dotnet with the build output and stack trace Unable to cast object of type 'Microsoft.Code 
Analysis.CSharp.Symbols.PublicModel.ArrayTypeSymbol' to type 'Microsoft.CodeAnalysis.INamedTypeSymbol'.   at Amazon.Lambda.Annotations.SourceGenerator.Models.TypeModelBuilder.Build(ITypeSymbol symbol, GeneratorExecutionContext context) [C:\Users\RenatoGolia\Develop 
ment\Labs\FindNationalityFunction\FindNationalityFunction.csproj]
    0 Warning(s)
    1 Error(s)

Time Elapsed 00:00:00.78
$ dotnet build --verbosity detailed
[...]
   1:7>CSC : error AWSLambda0001: This is a bug. Please run the build with detailed verbosity (dotnet build --verbosity detailed) and file a bug at https://github.com/aws/aws-lambda-dotnet with the build output and stack trace Unable to cast object of type 'Microso
       ft.CodeAnalysis.CSharp.Symbols.PublicModel.ArrayTypeSymbol' to type 'Microsoft.CodeAnalysis.INamedTypeSymbol'.   at Amazon.Lambda.Annotations.SourceGenerator.Models.TypeModelBuilder.Build(ITypeSymbol symbol, GeneratorExecutionContext context) [C:\Users\Renat 
       oGolia\Development\Labs\FindNationalityFunction\FindNationalityFunction.csproj]
         at Amazon.Lambda.Annotations.SourceGenerator.Models.TypeModelBuilder.<>c__DisplayClass0_0.<Build>b__0(ITypeSymbol arg)
         at System.Linq.Enumerable.SelectArrayIterator`2.ToList()
         at Amazon.Lambda.Annotations.SourceGenerator.Models.TypeModelBuilder.Build(ITypeSymbol symbol, GeneratorExecutionContext context)
         at Amazon.Lambda.Annotations.SourceGenerator.Models.LambdaMethodModelBuilder.Build(IMethodSymbol lambdaMethodSymbol, IMethodSymbol configureMethodSymbol, GeneratorExecutionContext context)
         at Amazon.Lambda.Annotations.SourceGenerator.Models.LambdaFunctionModelBuilder.Build(IMethodSymbol lambdaMethodSymbol, IMethodSymbol configureMethodSymbol, GeneratorExecutionContext context)
         at Amazon.Lambda.Annotations.SourceGenerator.Generator.Execute(GeneratorExecutionContext context).
         CompilerServer: server - server processed compilation - e5a406cb-a7d8-4ff4-a32b-542af9be04cf
[...]

Reproduction Steps

// Function.cs

using Amazon.Lambda.Core;
using Amazon.Lambda.Annotations;
using System.Text.Json.Serialization;
using System.Net.Http.Json;
using Microsoft.Extensions.DependencyInjection;

[assembly: LambdaSerializer(typeof(Amazon.Lambda.Serialization.SystemTextJson.DefaultLambdaJsonSerializer))]

namespace FindNationalityFunction;

public class Functions
{
    [LambdaFunction]
    public async Task<Country[]> GetCountriesAsync([FromServices] IHttpClientFactory httpClientFactory, string name)
    {
        var http = httpClientFactory.CreateClient("Nationality");

        var response = await http.GetFromJsonAsync<Response>($"https://api.nationalize.io/?name={name}");

        return response?.Countries ?? Array.Empty<Country>(); //<--- compiler error
    }
}

public record Response(
    [property: JsonPropertyName("country")] Country[] Countries,
    [property: JsonPropertyName("name")] string Name
);

public record Country(
    [property: JsonPropertyName("country_id")] string CountryCode,
    [property: JsonPropertyName("probability")] double Probability
);

[LambdaStartup]
public class Startup
{
    public void ConfigureServices(IServiceCollection services)
    {
        services.AddHttpClient("Nationality");
    }
}
// FindNationalityFunction.csproj

<Project Sdk="Microsoft.NET.Sdk">

  <PropertyGroup>
    <TargetFramework>net6.0</TargetFramework>
    <ImplicitUsings>enable</ImplicitUsings>
    <Nullable>enable</Nullable>
    <LangVersion>latest</LangVersion>
  </PropertyGroup>

  <ItemGroup>
    <PackageReference Include="Amazon.Lambda.Annotations" Version="0.6.0-preview" />
    <PackageReference Include="Amazon.Lambda.Core" Version="2.1.0" />
    <PackageReference Include="Amazon.Lambda.Serialization.SystemTextJson" Version="2.3.0" />
    <PackageReference Include="Microsoft.Extensions.Http" Version="7.0.0" />
  </ItemGroup>

</Project>

Possible Workaround

Returning a list works without problems

[LambdaFunction]
public async Task<List<Country>> GetCountriesAsync([FromServices] IHttpClientFactory httpClientFactory, string name)
{
    var http = httpClientFactory.CreateClient("Nationality");

    var response = await http.GetFromJsonAsync<Response>($"https://api.nationalize.io/?name={name}");

    return response?.Countries switch
    {
        null or [] => new List<Country>(),
        var items => new List<Country>(items)
    };
}

Additional Information/Context

No response

AWS .NET SDK and/or Package version used

Amazon.Lambda.Annotations: 0.6.0-preview Amazon.Lambda.Core: 2.1.0 Amazon.Lambda.Serialization.SystemTextJson: 2.3.0

Targeted .NET Platform

Lambda dotnet6 runtime

Operating System and version

Whatever Lambda uses

ashishdhingra commented 1 year ago

Reproducible. Needs review with the team.

Kralizek commented 1 year ago

The same error also occurs when the function returns T[] instead of Task<T[]>

Kralizek commented 1 year ago

@ashishdhingra any update?

ashishdhingra commented 1 year ago

@ashishdhingra any update?

@Kralizek Apologies for delay. This is currently being prioritised per my discussion with the team and should be fixed soon.

Kralizek commented 1 year ago

@ashishdhingra any update?

@Kralizek Apologies for delay. This is currently being prioritised per my discussion with the team and should be fixed soon.

Thanks! Sorry for the ping!

normj commented 1 year ago

@Kralizek This isn't reproducible in the latest (0.13.2) version of Amazon.Lambda.Annotations. Can you try again with the latest to make sure I'm not missing something. I know we have done a lot of rework on detecting Task usages so I think we might have addressed this issue by accident.

Kralizek commented 1 year ago

I'll try to check sometimes in the coming week.

normj commented 1 year ago

Thanks

normj commented 1 year ago

I'm going to close this as I really believe we fixed this with previous refactoring of the library. If you find the issue still exists feel free to reopen the issue or create a new one.

github-actions[bot] commented 1 year ago

⚠️COMMENT VISIBILITY WARNING⚠️

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.

Kralizek commented 1 year ago

Damn, I lost this ticket in the sea of reads and forgot to test it. My bad.

normj commented 1 year ago

@Kralizek No worries, I definitely understand.