spartycurse
spartycurse

Reputation: 33

Update JSON object

I am trying to read and update a JSON array from a file. But i am getting this error while trying to update the value of a property. - Property or indexer cannot be assigned to “--” it is read only

Here's my code -

var referenceFile = @"TestData\report.json";
var json1 = File.ReadAllText(referenceFile);

JArray jsonArray = JArray.Parse(json1);
JObject array = JObject.Parse(jsonArray[0].ToString());

foreach (var item in array)
{
    var x = item.Value;
    item.Value = "test"; // Error
}

My question is how can i update the JSON. this is the json file i need to update.

[
  {
    "description": "",
    "elements": [
      {
         "description": ""
            ],
    "id": "",
    "keyword": "Feature",
    "line": 1,
    "name": "Validate data via DB Connection",
    "uri": "dbtest/DB_Query.feature"
  }
]

Upvotes: 0

Views: 1040

Answers (4)

Amogh Sarpotdar
Amogh Sarpotdar

Reputation: 617

Answer provided by Guru Stron above should help! If you are using visual studio IDE, with your code -

foreach (var item in array)
        {
            var x = item.Value;
            item.Value = "test"; // Error
        }

the build failure occurs with clear explaination : 'Property or indexer 'KeyValuePair<string, JToken?>.Value' cannot be assigned to -- it is read only.

In short, with your code, you are trying to change something that is read only.

Upvotes: 0

Tom W
Tom W

Reputation: 5403

You are iterating a JObject - which you have called array and so the iterator type will be KeyValuePair<string, JToken>. The property KeyValuePair.Value has a getter only

I expect what you intended to do was loop over the properties of the object, so that the iterator type is JProperty. These are exposed through JObject.Properties().

Upvotes: 0

Arcord
Arcord

Reputation: 1909

Shouldn't you create an class that represent the JSON ?

In that case you could deserialize the JSON into a object, update it and serialize it again ?

var myObject JsonConvert.DeserializeObject<MyClass>(json1);
myObject.First().Description = "Hello" // Obviously you modify the field/value you want
var json2 JsonConvert.SerializeObject(myObject);

It will improve a lot the readibility instead of using the JArray/JObject.

Upvotes: 0

Guru Stron
Guru Stron

Reputation: 141600

With fixed json you can use Replace, for example to change all values to "test":

var json = @"[
  {
    ""description"": """",
    ""elements"": [
      {
         ""description"": """"
       }],
    ""id"": """",
    ""keyword"": ""Feature"",
    ""line"": 1,
    ""name"": ""Validate data via DB Connection"",
    ""uri"": ""dbtest/DB_Query.feature""
  }
]";

var jarr = JArray.Parse(json);
foreach(var jVal in jarr.Descendants().OfType<JValue>())
{
    jVal.Replace(new JValue("test"));
}

You will end up with next json for jarr:

[
  {
    "description": "test",
    "elements": [
      {
        "description": "test"
      }
    ],
    "id": "test",
    "keyword": "test",
    "line": "test",
    "name": "test",
    "uri": "test"
  }
]

If you want to change concrete property you can just use indexers:

jarr[0]["description"] = "test1"; // sets root "description" of first element to "test1"

Upvotes: 2

Related Questions