Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Adding new Jtoken to Json Jtoken

Tags:

json

c#

I have the following Json

{
  "error": {
    "errors": [
      {
        "domain": "global",
        "reason": "required",
        "message": "Login Required",
        "locationType": "header",
        "location": "Authorization"
      }
    ],
    "code": 401,
    "message": "Login Required"
  }
}

What I am trying to do is add a new JToken Under "message": "Login Required" something like "RetryMessage": "Failed after 10 retries"

I found this How do you add a JToken to an JObject? which doesn't quite work I think because of the fact that error is a token and not an object but I'm not sure.

What I have tried:

var JsonObj = JObject.Parse(response);
var RetryMessageJson = JToken.Parse(@"{ ""RetryMessage"" : ""UnKnown""}");
JsonObj["error"]["message"].AddAfterSelf(RetryMessageJson);

I have tried several versions of the code above and they all come back with the following Error message:

Newtonsoft.Json.Linq.JProperty cannot have multiple values.
like image 950
DaImTo Avatar asked May 22 '14 08:05

DaImTo


People also ask

Can not add JValue to JObject?

A JObject cannot directly contain a JValue , nor another JObject , for that matter; it can only contain JProperties (which can, in turn, contain other JObjects , JArrays or JValues ).

What is the difference between JObject and JToken?

So you see, a JObject is a JContainer , which is a JToken . Here's the basic rule of thumb: If you know you have an object (denoted by curly braces { and } in JSON), use JObject. If you know you have an array or list (denoted by square brackets [ and ] ), use JArray.

Is JArray a JToken?

JArray. FromObject(x) takes an object , so it can be used with anything that can be represented as an object and thus certainly an JToken.


2 Answers

Unless the ordering really matters, I suspect you just want to make it another property of the error:

// Variable names edited to follow normal C# conventions
var jsonResponse = JObject.Parse(response);
jsonResponse["error"]["retryMessage"] = "Unknown";

With your sample JSON, that results in:

{
  "error": {
    "errors": [
      {
        "domain": "global",
        "reason": "required",
        "message": "Login Required",
        "locationType": "header",
        "location": "Authorization"
      }
    ],
    "code": 401,
    "message": "Login Required",
    "retryMessage": "Unknown"
  }
}
like image 97
Jon Skeet Avatar answered Oct 22 '22 08:10

Jon Skeet


Although Jon Skeet's answer is 100% correct, in your situation you could accomplish the same thing without explicitly specifying the exact path:

var jsonResponse = JObject.Parse(response);
var newProperty = new JProperty("RetryMessage", "Failed after 10 retries");
jsonResponse.Last.AddAfterSelf(newProperty);
like image 31
Kaj Avatar answered Oct 22 '22 08:10

Kaj