using System; using System.Collections.Generic; using System.Dynamic; using System.Linq; using System.Text.Json; using System.Text.Json.Serialization; namespace PCL.Core.Utils; // Partly generated by o4-mini (20250611) // ReSharper disable All #nullable disable public sealed class ExpandoObjectConverter : JsonConverter { public static readonly ExpandoObjectConverter Default = new ExpandoObjectConverter(); public ExpandoObjectConverter() { } public override ExpandoObject Read( ref Utf8JsonReader reader, Type typeToConvert, JsonSerializerOptions options) { if (reader.TokenType == JsonTokenType.Null) { return null; } using (JsonDocument document = JsonDocument.ParseValue(ref reader)) { JsonElement root = document.RootElement; return Read(root, options); } } public static ExpandoObject Read( JsonElement element, JsonSerializerOptions options) { ExpandoObject expandoObject = new ExpandoObject(); IDictionary dict = expandoObject; foreach (JsonProperty property in element.EnumerateObject()) { dict.Add(property.Name, _ConvertElement(property.Value, options)); } return expandoObject; } private static object _ConvertElement(JsonElement element, JsonSerializerOptions options) { return element.ValueKind switch { JsonValueKind.Object => Read(element, options), JsonValueKind.Array => element.EnumerateArray() .Select(item => _ConvertElement(item, options)) .ToList(), JsonValueKind.String => element.GetString(), JsonValueKind.Number when element.TryGetInt64(out var integer) => integer, JsonValueKind.Number when element.TryGetDouble(out var number) => number, JsonValueKind.True => true, JsonValueKind.False => false, JsonValueKind.Null => null, JsonValueKind.Undefined => null, _ => element.GetRawText() }; } public override void Write( Utf8JsonWriter writer, ExpandoObject value, JsonSerializerOptions options) { if (value is null) { writer.WriteNullValue(); return; } writer.WriteStartObject(); foreach (KeyValuePair kvp in value) { writer.WritePropertyName(kvp.Key); JsonSerializer.Serialize(writer, kvp.Value, options); } writer.WriteEndObject(); } }