My application receives a JSON object as:
{
"names": [
"name_1",
"name_2"
]
}
I want to deserialize it to a list of Person object, defined as:
class Person
{
public string Name { set; get; }
}
Currently, I am deserializing the JSON object to a list of strings then create a list of Person manually like the following:
var names = JsonConvert.DeserializeObject<List<string>>(json);
var people = new List<Person>();
foreach(var name in names)
people.Add(new Person(){ Name = name });
Instead, I am interested in something like the following:
var people = JsonConvert.DeserializeObject<List<Person>>(json);
I am implementing the Person deserializer as:
public class PersonJsonConverter : JsonConverter
{
private readonly Dictionary<string, string> _propertyMappings;
public PersonJsonConverter()
{
_propertyMappings = new Dictionary<string, string>
{
{"name", nameof(Person.Name)}
};
}
public override bool CanConvert(Type objectType)
{
return objectType.GetTypeInfo().IsClass;
}
public override object ReadJson(
JsonReader reader,
Type objectType,
object existingValue,
JsonSerializer serializer)
{
object instance = Activator.CreateInstance(objectType);
var props = objectType.GetTypeInfo().DeclaredProperties.ToList();
JObject obj = JObject.Load(reader);
foreach (JProperty jsonProperty in obj.Properties())
{
if (!_propertyMappings.TryGetValue(jsonProperty.Name, out var name))
name = jsonProperty.Name;
PropertyInfo prop = props.FirstOrDefault(
pi => pi.CanWrite && pi.Name == name);
prop?.SetValue(
instance,
jsonProperty.Value.ToObject(prop.PropertyType, serializer));
}
return instance;
}
}
This deserializer can deserilize object such as:
{
"names": [
"name": "name_1",
"name": "name_2"
]
}
but not
{
"names": [
"name_1",
"name_2"
]
}
Note that my application can receive both types of JSON objects, so better to have a common deserializer for both types.
