Reputation: 5281
I am working with C# project in which, most data was of basic type all these days such as string, int, bool. Our client imprlements the JSON with System.Runtime.Serialization.Json, where we deserialize JSON sent from a server that is implemented in C++.
So for instance if I had to De-serialize a JSON sent from the server with 2 string keys such as:
{
"key1":"value1",
"key2":"value2"
}
we would define a class such as
[DataContract]
public class DeserializeKeys
{
[DataMember] public string key1 { get; set; }
[DataMember] public string key2 { get; set; }
};
Our server side code has changed to now send array of strings as a value as shown in the JSON object below:
{
"key1":"value1",
"key2":
[
"arrayValue1",
"arrayValue2",
"arrayValue3"
]
}
Please help me write a corresponding class that can deserialize the given JSON using "System.Runtime.Serialization.Json" class in C#.
I have already tried:
[DataContract]
public class DeserializeKeys
{
[DataMember] public string key1 { get; set; }
[DataMember] public string[] key2 { get; set; }
};
and
[DataContract]
public class DeserializeKeys
{
[DataMember] public string key1 { get; set; }
[DataMember] public List<string> key2 { get; set; }
};
but I am getting null
for key2
upon deserialization.
What is the right way to define a class so that the JSON deserialization of array of string happens just as it works currently for a single string.
Upvotes: 1
Views: 1260
Reputation: 6714
Seems to work correctly for me (both string[]
and List<string>
) i'll assume that you deserialized it in a wrong way. Here is a minimal example that should get your started on fixing your app.
using System;
using System.Collections.Generic;
using System.IO;
using System.Runtime.Serialization;
using System.Runtime.Serialization.Json;
using System.Text;
namespace Serializator
{
public class Serializator
{
static public SomeClass ReadToObject(string json)
{
MemoryStream ms = new MemoryStream(Encoding.UTF8.GetBytes(json));
DataContractJsonSerializer ser = new DataContractJsonSerializer(typeof(SomeClass));
var deserialized = ser.ReadObject(ms) as SomeClass;
ms.Close();
return deserialized;
}
}
[DataContract]
public class SomeClass
{
[DataMember] public string key1 { get; set; }
[DataMember] public List<string> key2 { get; set; }
};
class Program
{
static void Main(string[] args)
{
SomeClass sc = Serializator.ReadToObject("{\"key1\":\"value1\", \"key2\":[\"arrayValue1\", \"arrayValue2\", \"arrayValue3\"]}");
foreach(var item in sc.key2)
{
Console.WriteLine(item);
}
}
}
}
As it seems the issue lay in a data format not serialization mechanizm (the values of keys were also serialized objects) here is an updated version for the particular format the application required.
using System;
using System.Collections.Generic;
using System.IO;
using System.Runtime.Serialization;
using System.Runtime.Serialization.Json;
using System.Text;
namespace Serializator
{
public class Serializator
{
static public Object ReadToObject(string json, Type t)
{
MemoryStream ms = new MemoryStream(Encoding.UTF8.GetBytes(json));
DataContractJsonSerializer ser = new DataContractJsonSerializer(t);
var deserialized = ser.ReadObject(ms);
ms.Close();
return deserialized;
}
}
[DataContract]
public class IntermediateClass
{
[DataMember] public string error { get; set; }
[DataMember] public List<string> group { get; set; }
};
[DataContract]
public class ErrorClass
{
[DataMember] public string ErrorCode { get; set; }
[DataMember] public string ErrorMessage { get; set; }
};
public class GroupClass
{
[DataMember] public int ID { get; set; }
[DataMember] public string Name { get; set; }
}
public class CombinedClass
{
public ErrorClass error { get; set; }
public List<GroupClass> group { get; set; }
}
class Program
{
static void Main(string[] args)
{
CombinedClass cb = new CombinedClass();
IntermediateClass ic = (IntermediateClass)Serializator.ReadToObject("{\"error\":\"{\\n \\\"ErrorCode\\\" : 0,\\n \\\"ErrorMessage\\\" : \\\"Success.\\\"\\n}\\n\",\"group\":[\"{\\n \\\"ID\\\" : 1,\\n \\\"Name\\\" : \\\"Student1\\\"\\n}\\n\",\"{\\n \\\"ID\\\" : 2,\\n \\\"Name\\\" : \\\"Student2\\\"\\n}\\n\"]}", typeof(IntermediateClass));
cb.group = new List<GroupClass>();
foreach (var item in ic.group)
{
cb.group.Add((GroupClass)Serializator.ReadToObject(item, typeof(GroupClass)));
}
cb.error = (ErrorClass)Serializator.ReadToObject(ic.error, typeof(ErrorClass));
Console.WriteLine(cb.error.ErrorCode);
Console.WriteLine(cb.error.ErrorMessage);
Console.WriteLine(cb.group[0].Name);
Console.WriteLine(cb.group[0].ID);
Console.WriteLine(cb.group[1].Name);
Console.WriteLine(cb.group[1].ID);
}
}
}
Upvotes: 2