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

Custom JsonConverter breaks context variable in JsonSchemaExporterOptions.TransformSchemaNode callback #109868

Open
Peter-B- opened this issue Nov 15, 2024 · 1 comment
Labels
area-System.Text.Json untriaged New issue has not been triaged by the area owner

Comments

@Peter-B-
Copy link

Description

I expect JsonSchemaExporterOptions.TransformSchemaNode to be invoked once for each property of a class. The JsonSchemaExporterContext parameter should be set to the property.

When I add a custom JsonConverter to multiple properties, only the callback for the last property is invoked. It is invoked for each property with a custom JsonConverter.

Reproduction Steps

  • Create two classes C1 and C2
  • Assign a custom JsonConverter to each of these classes
  • Create another class named Test containing a property of each C1 and C2
  • Register a callback to JsonSchemaExporterOptions.TransformSchemaNode
    • Log the context.PropertyInfo and context.TypeInfo

Types

[JsonConverter(typeof(C1JsonConverter))]
public class C1 { }

[JsonConverter(typeof(C2JsonConverter))]
public class C2 { }

public class Test
{
    public C1 C1 { get; set; }
    public C2 C2 { get; set; }
}

Converters

public class C1JsonConverter:JsonConverter<C1>
{
    public override C1? Read(ref Utf8JsonReader reader, Type typeToConvert, JsonSerializerOptions options) => 
        new();

    public override void Write(Utf8JsonWriter writer, C1 value, JsonSerializerOptions options) => 
        writer.WriteStringValue("C1");
}

public class C2JsonConverter:JsonConverter<C2>
{
    public override C2? Read(ref Utf8JsonReader reader, Type typeToConvert, JsonSerializerOptions options) => 
        new();

    public override void Write(Utf8JsonWriter writer, C2 value, JsonSerializerOptions options) => 
        writer.WriteStringValue("C2");
}

Main

JsonSchemaExporterOptions exporterOptions = new()
{
    TransformSchemaNode = (context, schema) =>
    {
        Console.WriteLine($"Transform {context.TypeInfo.Type.Name} as {context.PropertyInfo?.Name}");

        return schema;
    }
};

var schema = JsonSerializerOptions.Web.GetJsonSchemaAsNode(typeof(Test), exporterOptions);
Console.WriteLine();
Console.WriteLine(schema.ToString());
Console.WriteLine();

Expected behavior

I expect to see one console message for each property:

Transform C1 as c1
Transform C2 as c2
Transform Test as

Actual behavior

The callback is invoked two times with the context of property Test.C2:

Transform C2 as c2
Transform C2 as c2
Transform Test as

Removing one or both of the custom JsonConverters will fix this issue.

Regression?

No response

Known Workarounds

No response

Configuration

  • dotnet SDK 9.0.100
  • Windows 11
  • x64
  • both Debug and Release
<Project Sdk="Microsoft.NET.Sdk">

  <PropertyGroup>
    <OutputType>Exe</OutputType>
    <TargetFramework>net9.0</TargetFramework>
    <ImplicitUsings>enable</ImplicitUsings>
    <Nullable>enable</Nullable>
  </PropertyGroup>

</Project>

Other information

No response

@dotnet-policy-service dotnet-policy-service bot added the untriaged New issue has not been triaged by the area owner label Nov 15, 2024
Copy link
Contributor

Tagging subscribers to this area: @dotnet/area-system-text-json, @gregsdennis
See info in area-owners.md if you want to be subscribed.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
area-System.Text.Json untriaged New issue has not been triaged by the area owner
Projects
None yet
Development

No branches or pull requests

1 participant