Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Json.net: Can JObject.SelectToken do the same thing the XPath can do? If yes what are the syntax?

The answer to the query posted in 2009 was to use a new feature JObject.SelectToken which is supposed to deliver XPath like functionality. I am now using JSON.NET 4.5 R11 and SelectToken method is available.

But I could not find much documentation (basically syntax) regarding the path string to be passed to SelectToken function.

Following code produces a Json string and on which I would like to execute a Xpath like method (i.e. to my knowledge SelectToken)

IList branches = new ArrayList();
IList employees = new ArrayList();
employees.Add(new { EmpId = 1, Name = "Name1" });
employees.Add(new { EmpId = 2, Name = "Name2" });
employees.Add(new { EmpId = 3, Name = "Name3" });
IList employees2 = new ArrayList();
employees2.Add(new { EmpId = 4, Name = "Name1" });
employees2.Add(new { EmpId = 5, Name = "Name5" });
branches.Add(new { BranchName = "Branch1", Employees = employees });
branches.Add(new { BranchName = "Branch2", Employees = employees });

string json = JsonConvert.SerializeObject(branches);

var branchesDeserialised = JsonConvert.DeserializeAnonymousType(json, new[] { new { BranchName = "", Employees = new[] { new { EmpId = 0, Name = "" } } } });

JArray ja = JArray.Parse(json);
var AllName1Tokens = ja.SelectToken(@"..Name=""Name1"""); //Get all names that are having Name = "Name1" irrespective of branch

Since I do not have the binaries of the classes and structure of the Json string is so huge that it will be difficult to use dynamic. So using LINQ on the objects after de-serialization is not possible. I do not want to convert the Json string to XML or some other format to do the selection either. Also i do not want to write code to parse it.

What are the syntax of the Path parameter of SelectToken function? How do I select all EmpId of employees where Name=”Name1”?

Edit1: Is it possible to get the result using JObject.Select (LINQ query) on JSON string (not on the real object) in case of SelectToken is not capable of doing it? What about regex?

like image 760
keyr Avatar asked Dec 08 '12 17:12

keyr


People also ask

What is JObject and JToken?

The JToken hierarchy looks like this: JToken - abstract base class JContainer - abstract base class of JTokens that can contain other JTokens JArray - represents a JSON array (contains an ordered list of JTokens) JObject - represents a JSON object (contains a collection of JProperties) JProperty - represents a JSON ...

How to query JToken?

SelectToken() provides a method to query LINQ to JSON using a single string path to a desired JToken. SelectToken makes dynamic queries easy because the entire query is defined in a string. SelectToken is a method on JToken and takes a string path to a child token.

What is JObject C#?

JObject. It represents a JSON Object. It helps to parse JSON data and apply querying (LINQ) to filter out required data. It is presented in Newtonsoft.

How use JSON path in C#?

JObject obj = JObject. Parse(person); To apply JSONPath expressions we can use the SelectToken method. As input of this method we need to pass a string with the JSONPath expression we want to use and, as output, it will return a JToken with the result (or null, in case nothing is found).


1 Answers

From author of JSON.NET:

Since Json.NET 6.0 supes up SelectToken with full support for JSONPath, an XPath like querying language for JSON.

JObject o = JObject.Parse(@"{
  ""Manufacturers"": [
    {
      ""Name"": ""Acme Co"",
      ""Products"": [
        {
          ""Name"": ""Anvil"",
          ""Price"": 50
        }
      ]
    },
    {
      ""Name"": ""Contoso"",
      ""Products"": [
        {
          ""Name"": ""Elbow Grease"",
          ""Price"": 99.95
        },
        {
          ""Name"": ""Headlight Fluid"",
          ""Price"": 4
        }
      ]
    }
  ]
}");

// manufacturer with the name 'Acme Co'
var acme = o.SelectToken("$.Manufacturers[?(@.Name == 'Acme Co')]");

More details on blog post

like image 195
ITmeze Avatar answered Nov 03 '22 19:11

ITmeze