Deserializing JSON into an Object

Deserialize JSON into Object C#

You can use Visual Studio 2013, 2015 to create your model classes from a json, I did it and I parsed the JSON fine.
To use this feature, you must have JSON/XML in your clipboard, put your cursor inside a .cs file and then use the option Edit > Paste Special > Paste JSON AS Classes

Paste Special JSON as classes

Look the code that was generated:

public class Rootobject
{
public Class1[] Property1 { get; set; }
}

public class Class1
{
public int Rk { get; set; }
public int Gcar { get; set; }
public int Gtm { get; set; }
public string Date { get; set; }
public string Tm { get; set; }
public string Where { get; set; }
public string Opp { get; set; }
public string Rslt { get; set; }
public string Inngs { get; set; }
public int PA { get; set; }
public int AB { get; set; }
public int R { get; set; }
public int H { get; set; }
public int Doubles { get; set; }
public int Triples { get; set; }
public int HR { get; set; }
public int RBI { get; set; }
public int BB { get; set; }
public int IBB { get; set; }
public int SO { get; set; }
public int HBP { get; set; }
public int SH { get; set; }
public int SF { get; set; }
public int ROE { get; set; }
public int GDP { get; set; }
public int SB { get; set; }
public int CS { get; set; }
public float BA { get; set; }
public float OBP { get; set; }
public float SLG { get; set; }
public float OPS { get; set; }
public int BOP { get; set; }
public float aLI { get; set; }
public float WPA { get; set; }
public float RE24 { get; set; }
public int DFSDK { get; set; }
public float DFSFD { get; set; }
public string Pos { get; set; }
}

In runtime to deserialize JSON into this object created from Visual Studio, you can use Newtonsoft.Json, you can install this using nuget with the following command:

Install-Package Newtonsoft.Json

Now you can deserialized it, using the gerenric method DeserializedObject from the static class JsconCovert, like that:

Rootobject object = JsonConvert.DeserializeObject<Rootobject>(jsonString); 

How to deserialize Json to an object?

var s = "{\r\n  \"Status\": \"PLANNED\"\r\n}";
var obj = Newtonsoft.Json.JsonConvert.DeserializeObject<StatusModel>(s);

The model you have defined is incorrect.
Your model should be like this:

public class StatusModel
{
public string Status { get; set; }
}

Now value will be extracted to this model and you can access the value like:

var value = obj.Status; //"PLANNED"

Deserialize JSON into any object

I have acheived something similar using Newtonsoft

Your route should take the body in as a generic object and it can then be deserialized into any object you'd like:

/*Using this method, the controller will automatically handle
validating proper Json format*/
[HttpPost]
public async Task<IActionResult> Post([FromBody] object Body)
{

/*here you will send the generic object to a service which will deserialize.
the object into an expected model.*/

customService.HandlePost(Body);
}

Now create an object with any expected fields you would get from the body. (Json2csharp.com is extremely useful!)

public class MessageBody    
{
public string Token { get; set; }
public string Name { get; set; }

}

Inside your service you can handle the object like this:

using Newtonsoft.Json
using Models.MessageBody

public class customService()
{

public void HandlePost(object body)
{

var DeserializedBody = JsonConvert.DeserializeObject<MessageBody>(body);

//Any Values that were not assigned will be null in the deserialized object
if(DeserializedBody.Name !== null)
{
//do something
}

}

}

This is obviously a very bare bones implementation, error handling will be important to catch any invalid data. Instead of using one object and null fields to get the data you need, I would recommend adding a "subject" route variable (string) that you can use to determine which object to deserialize the body into.

post *api/MessageBody/{Subject}

How Can I deserialize a json into a structure?

Yet another solution could be to make use of the JsonSchema

First let's redefine your data model:

public abstract class Settings
{
[JsonProperty("id")]
public string Id { get; set; }

[JsonProperty("type")]
public string Type { get; set; }
}

public class SettingsV1 : Settings
{
[JsonProperty("content")]
public string Content { get; set; }
}

public class SettingsV2 : Settings
{
[JsonProperty("content")]
public Content Content { get; set; }
}

public class Content
{
[JsonProperty("id")]
public string Id { get; set; }

[JsonProperty("duration")]
public long Duration { get; set; }
}
  • Instead of having a middle man (ContentStructure) rather than you can have two separate Settings versions
  • The common fields are defined inside the abstract base class

Now, you can use these two versioned classes to define json schemas:

private static JSchema schemaV1;
private static JSchema schemaV2;

//...
var generator = new JSchemaGenerator();
schemaV1 = generator.Generate(typeof(SettingsV1));
schemaV2 = generator.Generate(typeof(SettingsV2));

Finally all you need to do is to do a preliminary check before calling the DeserializeObject with the proper type:

Settings settings = null;
var semiParsed = JObject.Parse(json);
if (semiParsed.IsValid(schemaV1))
{
settings = JsonConvert.DeserializeObject<SettingsV1>(json);
}
else if (semiParsed.IsValid(schemaV2))
{
settings = JsonConvert.DeserializeObject<SettingsV2>(json);
}
else
{
throw new NotSupportedException("The provided json format is not supported");
}

Deserialize a JSON into a list of C# objects

The best move would be deserializing it as Dictionary<string, object> and Iterate through the values and casting them to your desired "Item" class.

JSON Deserialization issue : Error deserialize JSON value into type

The type of the value C is String, so the object mapper escapes all illegal characters a wraps the string in quotes.

You could make C an another map:

Map<String, Object> c = new HashMap<>();
c.put("a", 3);
c.put("b", 5);

Map<String, Object> m = new HashMap<>();
m.put("a", "b");
m.put("c", c);

Or you can create custom POJO and use @JsonRawValue annotation:

public class MyPojo{

private String a;

@JsonRawValue
private String c;

// getter and setters
}

MyPojo m = new MyPojo();
m.setA("b");
m.setB("{\"a\" :3, \"b\" : 5}");

objectmapper.writeValueAsString(m);

From the documentation:

Marker annotation that indicates that the annotated method or field should be serialized by including literal String value of the property as is, without quoting of characters. This can be useful for injecting values already serialized in JSON or passing javascript function definitions from server to a javascript client.
Warning: the resulting JSON stream may be invalid depending on your input value.

The client error meaning probably is that it can't deserialize String into an Object (it expects { instead of ").



Related Topics



Leave a reply



Submit