2

How can I deserialize a string to Json object where the json Object can be a single or an array, right now I have this, which works but its a hack (pseudo):

class MyObject{
  public string prop1
  public string prop2;
 }

 class MyList{
  List<MyObject> objects {get; set; }
 }

 class Test{
   MyList list = JsonSerialzer.Deserialize<MyList>(str);
   //if list is null - it can be single
   if(list == null){
      MyObject myObject = JsonSerializer.Deserialize<MyObject>(str);
      if(myObject != null)
         list.add(myObject);
     }
  }

As shown above, problem is the json String I am receiving from another service can be either single or list. How to handle this elegantly?

user1529412
  • 3,616
  • 7
  • 26
  • 42
  • 2
    The problem lies more in your JSON message, an attribute should always be either 1 object or an array. If it's an array and the result set only has one result then it should still be encapsulated in an array so you can't run into the problem you're having. Here's another high listed SO answer which could help you http://stackoverflow.com/questions/7895105/deserialize-json-with-c-sharp – Marthyn Olthof Jun 20 '16 at 14:51
  • Isn't the link you sent me the same exact thing I have? – user1529412 Jun 20 '16 at 15:06
  • Maybe, i didnt compare. But the answer under here is the correct answer to your SO. – Marthyn Olthof Jun 22 '16 at 12:51

1 Answers1

4

I would strongly advise against accepting different structures in the same argument, it makes your software highly brittle and unpredictable. But if it could be a list you can just check the first char is a [, e.g:

if (str.TrimStart().StartsWith("["))
{
    MyList list = JsonSerialzer.Deserialize<MyList>(str);
}
else
{
    MyObject myObject = JsonSerializer.Deserialize<MyObject>(str);
}

Also please note that by default all ServiceStack text serializers only serialize public properties, so you need to add getters/setters to each property you want serialized, e.g:

class MyObject
{
    public string prop1 { get; set; }
    public string prop2 { get; set; }
}

class MyList
{
    List<MyObject> objects { get; set; }
}

Otherwise you can configure ServiceStack.Text to also serialize public fields with:

JsConfig.IncludePublicFields = true;
mythz
  • 141,670
  • 29
  • 246
  • 390