Json Serialize/Deserialize to retain the type of property object within a class

48 Views Asked by At

I don't have much Json serialization/deserialization, but this has become a real issue and I can't help feeling that I'm missing something...

When I serialize an object, which has an object as a property, the object type isn't retained and therefore when deserialized isn't the correct object type. How do I ensure that the correct object type property is serialized/deserialized?

Example object to Json:

public class InfoPoint
{
    public string Name { get; set; } = string.Empty;
    public object? Value { get; set; }
    public string Location { get; set; } = string.Empty;
}

Program to show the issue:

List<InfoPoint> infoPoints = new List<InfoPoint>();

InfoPoint infoPoint1 = new InfoPoint();
infoPoint1.Name = "Point1";
bool status = true;
infoPoint1.Value = status;
infoPoint1.Location = "Main Switch Status";
infoPoints.Add(infoPoint1);

InfoPoint infoPoint2 = new InfoPoint();
infoPoint2.Name = "Point2";
UInt16 volume = 75;
infoPoint2.Value = volume;
infoPoint2.Location = "Volume Dial";
infoPoints.Add(infoPoint2);

InfoPoint infoPoint3 = new InfoPoint();
infoPoint3.Name = "Point3";
float[] sliders = new float[] { 2.3f, 1.79f, 8.77f, 5.5f };
infoPoint3.Value = sliders;
infoPoint3.Location = "Fader Panel";
infoPoints.Add(infoPoint3);

JsonSerializerSettings settings
    = new JsonSerializerSettings()
    {
        TypeNameHandling = TypeNameHandling.All,
        NullValueHandling = NullValueHandling.Ignore,
        Formatting = Formatting.Indented
    };

Console.WriteLine(JsonConvert.SerializeObject(infoPoint1, settings));
Console.WriteLine(JsonConvert.SerializeObject(infoPoint2, settings));
Console.WriteLine(JsonConvert.SerializeObject(infoPoint3, settings));
Console.WriteLine(JsonConvert.SerializeObject(infoPoints, settings));

Then the ouput:

{
  "$type": "JsonObjectListTest.InfoPoint, JsonObjectListTest",
  "Name": "Point1",
  "Value": true,
  "Location": "Main Switch Status"
}
{
  "$type": "JsonObjectListTest.InfoPoint, JsonObjectListTest",
  "Name": "Point2",
  "Value": 75,
  "Location": "Volume Dial"
}
{
  "$type": "JsonObjectListTest.InfoPoint, JsonObjectListTest",
  "Name": "Point3",
  "Value": {
    "$type": "System.Single[], System.Private.CoreLib",
    "$values": [
      2.3,
      1.79,
      8.77,
      5.5
    ]
  },
  "Location": "Fader Panel"
}
{
  "$type": "System.Collections.Generic.List`1[[JsonObjectListTest.InfoPoint, JsonObjectListTest]], System.Private.CoreLib",
  "$values": [
    {
      "$type": "JsonObjectListTest.InfoPoint, JsonObjectListTest",
      "Name": "Point1",
      "Value": true,
      "Location": "Main Switch Status"
    },
    {
      "$type": "JsonObjectListTest.InfoPoint, JsonObjectListTest",
      "Name": "Point2",
      "Value": 75,
      "Location": "Volume Dial"
    },
    {
      "$type": "JsonObjectListTest.InfoPoint, JsonObjectListTest",
      "Name": "Point3",
      "Value": {
        "$type": "System.Single[], System.Private.CoreLib",
        "$values": [
          2.3,
          1.79,
          8.77,
          5.5
        ]
      },
      "Location": "Fader Panel"
    }
  ]
}

Point2 holds an object of type UInt16, I need it to retain that type when deserialized. I've done a lot of research, but how do I serialize and deserialize to retain the resulting property as a UInt16. It's vital that the object type of property "Value" is correct.

Any help appreciated...

0

There are 0 best solutions below