问题
I'm having trouble getting the new System.Text.Json
to deserialize collections stored on read-only properties.
Consider these classes:
public class SomeItem {
public string Label { get; set; }
}
public class SomeObjectWithItems {
public string Label { get; set; }
// Note this property is read-only but the collection it points to is read/write
public ObservableCollection<SomeItem> Items { get; }
= new ObservableCollection<SomeItem>();
}
Here's the JSON:
{
"Label": "First Set",
"Items": [
{
"Label": "Item 1"
},
{
"Label": "Item 2"
},
{
"Label": "Item 3"
},
{
"Label": "Item 4"
}
]
}
Here's the code I'm running...
var json = ...;
var obj = JsonSerializer.deserialize<SomeObjectWithItems>(json);
Debug.WriteLine($"Item Count for '{obj.label}': {obj.Items.Count}");
The above outputs the following:
Item Count for 'First Set': 0
If I change Items
to be read/write, then it works, but so many of our models have read-only properties that hold mutable collections so I'm wondering if we can even use this.
Note: Json.NET handles this correctly, internally calling the 'Add' method on the existing collection rather than creating a new one, but I don't know how to achieve that outside of writing custom converters for all the classes we have defined.
回答1:
This is by design for collections that don't have a setter. To avoid issues with adding to pre-populated collections (that the serializer doesn't instantiate) the deserializer uses "replace" semantics which requires the collection to have a setter.
Source: https://github.com/dotnet/corefx/issues/41433
There is currently an open issue for Support adding to collections if no setter
https://github.com/dotnet/corefx/issues/39477
My recommendation is continue to use Json.NET
in this case unless you want to write a customer converter.
来源:https://stackoverflow.com/questions/59748093/can-system-text-json-jsonserializer-serialize-collections-on-a-read-only-propert