Ivan-Mark Debono
Ivan-Mark Debono

Reputation: 16320

Deserializing array of JSONElement back to a concrete list not working when using System.Text.Json

I have a problem when deserializing an object. The object has a property (data) that is a list of JSONElement. I'm doing:

using var doc = JsonDocument.Parse(JsonSerializer.Serialize(result));

var e = doc.RootElement.GetProperty("data");
var data = JsonSerializer.Deserialize<List<MyItem>>(e);

The serialized result variable has the following content:

{
   "data":[
      {
         "id":245,
         "number":14,
         "name":"Test"
      }
   ],
   "totalCount":-1,
   "groupCount":-1,
   "summary":null
}

And the MyItem class is as follows:

public class MyItem
{
    public int Id { get; set; }
    public int Number { get; set; }
    public string Name { get; set; }
}

The data variable is a list with x items. However all items are empty instances.

What am I doing wrong?

Upvotes: 1

Views: 2520

Answers (2)

Serge
Serge

Reputation: 43931

Everythig can be done in one string of code. You just need to set PropertyNameCaseInsensitive = true of JsonSerializerOptions. Better to make it in a startup file.

List<MyItem> data =  JsonDocument.Parse(json).RootElement.GetProperty("data")
.Deserialize<List<MyItem>>();

Upvotes: 0

Mark Cilia Vincenti
Mark Cilia Vincenti

Reputation: 1614

The problem is likely that your data is using lowercase property names which are not translated to the property names in your class with the default deserialization settings.

using System.Text.Json;

dynamic result = new
{
    data = new dynamic[] {
        new {
            id = 245,
            number = 14,
            name = "Test"
        }
    },
    totalCount = -1,
    groupCount = -1
};

using var doc = JsonDocument.Parse(JsonSerializer.Serialize(result));

var e = doc.RootElement.GetProperty("data");
List<MyItem> data = JsonSerializer.Deserialize<List<MyItem>>(e);

Console.WriteLine($"{data.First().Id} {data.First().Number} {data.First().Name}");

The above code won't work with your MyItem class, but try this instead:

public class MyItem
{
    [JsonPropertyName("id")]
    public int Id { get; set; }
    [JsonPropertyName("number")]
    public int Number { get; set; }
    [JsonPropertyName("name")]
    public string Name { get; set; }
}

If it works, either use the JsonPropertyName on all your properties or else consider changing your deserialization options.

Upvotes: 2

Related Questions