dotnet / orleans

Cloud Native application framework for .NET
https://docs.microsoft.com/dotnet/orleans
MIT License
10.06k stars 2.03k forks source link

[Proposal] GenerateSerializer understanding and inclusion of primary constructor arguments #7819

Closed koenbeuk closed 2 years ago

koenbeuk commented 2 years ago

If we're willing to make the assumption that primary constructor arguments are in most cases desired to be included in the serialization process, we can make an exception in the code generation aspect such that primary constructor arguments are automatically included and assigned an Id from a special range:

[GenerateSerializer]
record Person([property: Id(0)] string FirstName, [property: Id(1)] string LastName)
{
    [Id(2)]
    public string? MiddleName { get; init; }
}

Can be compacted as:

[GenerateSerializer]
record Person(string FirstName, string LastName) {
    [Id(0)]
    public string? MiddleName { get; init; }
}

Open questions

Alternatives

Originally posted by @koenbeuk in https://github.com/dotnet/orleans/discussions/7569#discussioncomment-2988232

ReubenBond commented 2 years ago

Come to think of it, there is a "cake and eat it too" alternative, but it may require some more elaborate code generation and may not be worthwhile for that reason. Orleans supports reusing ids between levels in an inheritance hierarchy. It distinguishes between each level with a control character, ExtendedWireType.EndBaseFields (emitted via writer.WriteEndBase()). We could encode records in two logical parts, separated via an EndBaseFields tag. That would allow the ids in the primary constructor to be logically distinct from ids in the body, and therefore allow for overlapping ids.

ghost commented 2 years ago

We're moving this issue to the 4.0-Planning milestone for future evaluation / consideration. Because it's not immediately obvious that this is a bug in our framework, we would like to keep this around to collect more feedback, which can later help us determine the impact of it. We will re-evaluate this issue, during our next planning meeting(s). If we later determine, that the issue has no community involvement, or it's very rare and low-impact issue, we will close it - so that the team can focus on more important and high impact issues.