From 9ed987c54a1e216a69110b10e8e25e792a3714c6 Mon Sep 17 00:00:00 2001 From: ttu Date: Sat, 5 Oct 2024 09:06:12 +0300 Subject: [PATCH] Fixes for nested array handling --- .../ExpandoObjectConverter.cs | 76 ++++++++++++++----- JsonFlatFileDataStore/ObjectExtensions.cs | 15 +++- 2 files changed, 73 insertions(+), 18 deletions(-) diff --git a/JsonFlatFileDataStore/ExpandoObjectConverter.cs b/JsonFlatFileDataStore/ExpandoObjectConverter.cs index 4fc4549..44e385e 100644 --- a/JsonFlatFileDataStore/ExpandoObjectConverter.cs +++ b/JsonFlatFileDataStore/ExpandoObjectConverter.cs @@ -152,24 +152,66 @@ private static void AddPropertyToExpando(IDictionary expando, st var nestedArray = new List(); foreach (var nestedArrayElement in arrayElement.EnumerateArray()) { - if (nestedArrayElement.ValueKind == JsonValueKind.Object) + switch (nestedArrayElement.ValueKind) { - var nestedExpandoInNestedArray = new ExpandoObject(); - var nestedDictionaryInNestedArray = (IDictionary)nestedExpandoInNestedArray; - foreach (var nestedPropertyInNestedArray in nestedArrayElement.EnumerateObject()) - { - AddPropertyToExpando(nestedDictionaryInNestedArray, nestedPropertyInNestedArray.Name, nestedPropertyInNestedArray.Value); - } - nestedArray.Add(nestedExpandoInNestedArray); - } - else if (nestedArrayElement.ValueKind == JsonValueKind.Array) - { - // Recursively handle deeper nested arrays - nestedArray.Add(ProcessNestedArray(nestedArrayElement)); - } - else - { - nestedArray.Add(nestedArrayElement.ToString()); + case JsonValueKind.Undefined: + case JsonValueKind.Null: + nestedArray.Add(null); + break; + + case JsonValueKind.False: + nestedArray.Add(false); + break; + + case JsonValueKind.True: + nestedArray.Add(true); + break; + + case JsonValueKind.Number: + if (nestedArrayElement.TryGetInt32(out int nestedArrayElementIntValue)) + { + nestedArray.Add(nestedArrayElementIntValue); + } + else if (nestedArrayElement.TryGetInt64(out long longValue)) + { + nestedArray.Add(longValue); + } + else if (nestedArrayElement.TryGetDouble(out double doubleValue)) + { + nestedArray.Add(doubleValue); + } + else if (nestedArrayElement.TryGetDecimal(out decimal decimalValue)) + { + nestedArray.Add(decimalValue); + } + else + { + throw new JsonException("Unsupported numeric type"); + } + break; + + case JsonValueKind.String: + nestedArray.Add(nestedArrayElement.GetString()); + break; + + case JsonValueKind.Object: + + var nestedExpandoInNestedArray = new ExpandoObject(); + var nestedDictionaryInNestedArray = (IDictionary)nestedExpandoInNestedArray; + foreach (var nestedPropertyInNestedArray in nestedArrayElement.EnumerateObject()) + { + AddPropertyToExpando(nestedDictionaryInNestedArray, + nestedPropertyInNestedArray.Name, + nestedPropertyInNestedArray.Value); + } + nestedArray.Add(nestedExpandoInNestedArray); + break; + + case JsonValueKind.Array: + // Recursively handle deeper nested arrays + nestedArray.Add(ProcessNestedArray(nestedArrayElement)); + break; + } } arrayValues.Add(nestedArray); diff --git a/JsonFlatFileDataStore/ObjectExtensions.cs b/JsonFlatFileDataStore/ObjectExtensions.cs index 47d13be..e22a770 100644 --- a/JsonFlatFileDataStore/ObjectExtensions.cs +++ b/JsonFlatFileDataStore/ObjectExtensions.cs @@ -240,9 +240,20 @@ private static void HandleTypedEnumerable(object source, object destination, dyn if (targetType.GetTypeInfo().IsValueType || targetType == typeof(string) || IsDictionary(targetType) || IsEnumerable(targetType)) targetArray[i] = sourceValue; + else if (IsDictionary(type)) + targetArray[i] = sourceValue; // TODO: Should we copy child items instead of just replacing? + else if (IsEnumerable(type)) + targetArray[i] = sourceValue; // TODO: Should we copy child items instead of just replacing? else CopyProperties(sourceValue, targetArray[i]); } + + // TODO: What about this? This is not mentioned in the documentation? + // If list are not equal length, erase items from the end of the source + // while (targetArray.Count > sourceArray.Count) + // { + // targetArray.RemoveAt(targetArray.Count - 1); + // } } private static void HandleTypedDictionary(object source, object destination, PropertyInfo targetProperty, dynamic srcProp) @@ -409,7 +420,9 @@ private static IEnumerable GetProperties(object source) return expandoObject .Select(i => new { - Name = i.Key, Value = i.Value, PropertyType = i.Value?.GetType() + Name = i.Key, + Value = i.Value, + PropertyType = i.Value?.GetType() }) .ToList(); }