ShedSpotter
ShedSpotter

Reputation: 86

How to deserialize a List(Of Object) from JSON?

I have a List(Of Object) that I am using in a property of type IEnumerable(Of Object). I can serialize it fine but cannot work out then how to deserialize it from JSON back to a List(Of Object). Any help would be really great please.

My ViewModel:

Public Class ViewModel
    Inherits ViewModelBase

    Public Class MapSettings
        <Display(Name:="Map Name", Description:="Enter a optional name for the map.", GroupName:="Map Settings")>
        Public Property MapName As String
        <Display(Name:="Map Description", Description:="Enter a optional description for the map.", GroupName:="Map Settings")>
        Public Property MapDescription As String

        <Display(Name:="Map Comments", Description:="Enter optional comments for the map.", GroupName:="Map Settings")>
        Public Property MapComments As String

        <Display(Name:="Map Version", Description:="Enter a optional version for the map.", GroupName:="Map Settings")>
        Public Property MapVersion As String
    End Class

    Public Class GeneralSettings
        <Display(Name:="Route Colour", Description:="Sets the colour of the routes design line on the map.", GroupName:="General Settings")>
        Public Property Foreground As Color

    End Class

    Private _myItems() As IEnumerable(Of Object)
    Public Property MyItems() As IEnumerable(Of Object)
        Get
            If _myItems Is Nothing Then
                Return New List(Of Object)() From {
                          New MapSettings,
                          New GeneralSettings With {.Foreground = Colors.Blue}
                      }
            Else
                Return _myItems
            End If

        End Get
        Set(value As IEnumerable(Of Object))
            _myItems = value
            OnPropertyChanged()
        End Set

    End Property
End Class

My serialize code that I cannot complete:

Dim MyItems_New = JsonConvert.DeserializeObject(Of MyItems???)(MyJsonString)

JSON:

{
  "MyItems": [
    {
      "MapName": null,
      "MapDescription": null,
      "MapComments": null,
      "MapVersion": null
    },
    {
      "Foreground": "#FF0000FF"
    }
  ]
}

Upvotes: 0

Views: 653

Answers (1)

Visual Vincent
Visual Vincent

Reputation: 18310

I just found that Newtonsoft has built-in support for type handling, which can be enabled by setting the JsonSerializerSettings.TypeNameHandling property and passing it to the serialization methods. As long as you control the input, this should let you both serialize and deserialize your list without a problem.

Serialize:

Dim myItems = JsonConvert.SerializeObject(myVM.MyItems, Formatting.None, New JsonSerializerSettings() With { .TypeNameHandling = TypeNameHandling.Auto })

Deserialize:

Dim myItems_New = JsonConvert.DeserializeObject(Of List(Of Object))(MyJsonString, New JsonSerializerSettings() With { .TypeNameHandling = TypeNameHandling.Auto })

In your question, MyJsonString appears to be a serialized version of your ViewModel class rather than just the list itself. If this is the case, change DeserializeObject(Of List(Of Object)) to DeserializeObject(Of ViewModel).

Resulting JSON:

[
  {
    "$type": "MapSettings, YourProjectNamespace",
    "MapName": "New York",
    "MapDescription": "Map over New York",
    "MapComments": null,
    "MapVersion": "v1"
  },
  {
    "$type": "GeneralSettings, YourProjectNamespace",
    "Foreground": "#FF0000"
  }
]

Try it online (C#):
https://dotnetfiddle.net/0jCIGL

However, if these two classes are all you are planning to use this list for, then you'd be better off using something along the lines of Jimi's proposed solution, as then you're always working with strongly-typed objects.

Upvotes: 1

Related Questions