Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

F#: Fixing code generation for enum style discriminated unions and for discriminated unions with 4 of more cases #9095

Merged
merged 2 commits into from
Jul 31, 2024

Conversation

gfix
Copy link
Contributor

@gfix gfix commented Jul 31, 2024

This PR fixes code generation for the two remaining "flavors" of discriminated unions (DU) which currently do
not work. The two remaining "flavors" are enum style discriminated unions, and discriminated unions with 4 or more
cases. The key takeaway is that both these "flavors" of DUs have an int _tag backing field for the Tag property
which we must serialize/deserialize. For other types of DUs the Tag property is not backed by a backing field,
and we only need to serialize/deserialize the item{int}.

Enum style discriminated unions

Enum style DUs are not based on inheritance, and they do not have an Item{int} property, only a Tag property.
This tag must be used when serializing/deserializing.

Discriminated unions with 4 or more cases

When a fourth case is introduced in the DU, the abstract base class which all the cases inherit from gets a _tag
backing field for the Tag property. This must be serialized/deserialized as well, in addition to the Item{int}
in each of the concrete cases.

Switching to identifying the backing fields directly rather than properties

When identifying the data we need to serialize/deserialize in FSharpUnionCaseTypeDescription.GetUnionCaseDataMembers,
rather than looking for the properties Item{int} and Tag we go looking directly for the backing fields
item{int} and _tag. Since single, double and triple case DUs do not have a backing field for the Tag property,
and we do not have to serialize/deserialize the tag for these "flavors" anyway, it makes it easier to look for the backing
fields directly. That way, we don't have to treat the different "flavors" of DU separately. We serialize/deserialize
all items{int}, regardless of where they reside, and the _tag, if it exists (enum style and 4 or more cases).

Microsoft Reviewers: Open in CodeFlow

Fixes #8752
Fixes #8255

Copy link
Member

@ReubenBond ReubenBond left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM!

@ReubenBond ReubenBond merged commit 4ff9f62 into dotnet:main Jul 31, 2024
22 checks passed
@gfix gfix deleted the fsharpserialization branch August 1, 2024 06:40
@github-actions github-actions bot locked and limited conversation to collaborators Aug 31, 2024
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Labels
None yet
Projects
None yet
2 participants