Mich
Mich

Reputation: 3594

How to parse unknown Json file with Json.net in C#

I'm able to get a dynamic Json object using

dynamic obj = JsonConvert.DeserializeObject(json);

It seems to be a nested object structure

I need to graph every variable in the json file, but the json file structure changes often

Is there a way to parse through this structure using nested foreach() statements? If not, can can I parse it by accessing each element via a string like a Dictionary?

for example something like:

if(obj["Item1"]["Parameter3"]["Value2"]` != NULL)
   int number = obj["Item1"]["Parameter3"]["Value2"]`

Thanks,

Upvotes: 1

Views: 2941

Answers (2)

Mich
Mich

Reputation: 3594

Finally figured this api out

Some JToken entries have a list of values, others have a name and value. You have to sort which one is which prior to parsing it.

This will create a Dictionary with every entry in the Json file

    void SomeFunction()
    {
        Dictionary<string, decimal> json_data = new Dictionary<string, decimal>();
        dynamic json_obj = JsonConvert.DeserializeObject(json);
        Linearize(ref json_data, json_obj);
    }

    void Linearize(ref Dictionary<string, decimal> input_dict, JToken json_data, string key = "")
    {
        int i;
        if (json_data != null)
        {
            if (json_data.HasValues)
            {
                i = 0;
                foreach (dynamic entry in json_data)
                {
                    //Add a Name field if it exists
                    Type typeOfDynamic = entry.GetType();
                    if (typeOfDynamic.GetProperties().Where(p => p.Name.Equals("Name")).Any())
                        key += entry.Name + ".";

                    //If JToken is an Array
                    if (((JToken)entry).HasValues)
                    {
                        Linearize(ref input_dict, entry, key + "[" + i++ + "]" + ".");
                    }

                    //If JToken is a data type
                    else if (entry.Type == JTokenType.String || entry.Type == JTokenType.Float || entry.Type == JTokenType.Integer)
                    {
                        decimal output;
                        if (decimal.TryParse(entry.ToString(), out output))
                            input_dict.Add(key + "[" + i++ + "]", output);
                    }
                }
            }
        }           
    }

Upvotes: 0

Tim
Tim

Reputation: 2912

Yes there is an API for querying dynamically. See the documentation here: https://www.newtonsoft.com/json/help/html/QueryingLINQtoJSON.htm

Code looks something like this:

JObject rss = JObject.Parse(json); 
var postTitles =
    from p in rss["channel"]["item"]
    select (string)p["title"];

Upvotes: 2

Related Questions