I'm attempting to perform operations (update values, delete keys, add keys, etc.) on JSON data which I do not know anything about. These items are essentially property files and not JSON data returned from an application. These files could be very different and I need to develop a method that can perform these operations without knowing anything about the JSON data.
I am keeping track of the path of where the key is stored. If I had sample data as shown below, I would store the path like '/key1/innerKey5/' and get the data with the key innerKey6 using getNodeData.
If I had the path and the key of the item, how can I programmatically find this item in the JSON data and delete or update the item?
var originalData = someMethodToGetJSONData();
var currentData; // Global variable storing a copy of the original data which can be modified
json = {
"key1": {
"innerKey1": {
"innerKey2" : {
"innerKey3": "value1",
"innerKey4": "value2"
}
},
"innerKey5": {
"innerKey6": "value1"
}
},
"key2": "value3",
"key3": "value4"
}
function getKeysFromPath(keyPath) {
var split = keyPath.split('/');
var keys = [];
for(var i = 0; i < split.length; i++) {
if(split[i] != '') {
keys.push(split[i]);
}
}
return keys
}
function getNodeData(keyPath) {
var keys = getKeysFromPath(keyPath);
nodeData = currentItemData;
for(var i = 0; i < keys.length; i++) {
nodeData = nodeData[keys[i]];
}
return nodeData;
}
data = getNodeData('/key1/innerKey5/');
key = 'innerKey6';
console.log('Data: ' + data[key]);
I'm attempting to perform operations (update values, delete keys, add keys, etc.) on JSON data which I do not know anything about. These items are essentially property files and not JSON data returned from an application. These files could be very different and I need to develop a method that can perform these operations without knowing anything about the JSON data.
I am keeping track of the path of where the key is stored. If I had sample data as shown below, I would store the path like '/key1/innerKey5/' and get the data with the key innerKey6 using getNodeData.
If I had the path and the key of the item, how can I programmatically find this item in the JSON data and delete or update the item?
var originalData = someMethodToGetJSONData();
var currentData; // Global variable storing a copy of the original data which can be modified
json = {
"key1": {
"innerKey1": {
"innerKey2" : {
"innerKey3": "value1",
"innerKey4": "value2"
}
},
"innerKey5": {
"innerKey6": "value1"
}
},
"key2": "value3",
"key3": "value4"
}
function getKeysFromPath(keyPath) {
var split = keyPath.split('/');
var keys = [];
for(var i = 0; i < split.length; i++) {
if(split[i] != '') {
keys.push(split[i]);
}
}
return keys
}
function getNodeData(keyPath) {
var keys = getKeysFromPath(keyPath);
nodeData = currentItemData;
for(var i = 0; i < keys.length; i++) {
nodeData = nodeData[keys[i]];
}
return nodeData;
}
data = getNodeData('/key1/innerKey5/');
key = 'innerKey6';
console.log('Data: ' + data[key]);
Share
Improve this question
edited Oct 2, 2016 at 23:47
Jeff
asked Oct 2, 2016 at 23:35
JeffJeff
5204 silver badges21 bronze badges
3
-
2
Pet peeve: JSON object has only two properties:
parse
andstringify
. You have a JavaScript object, or just an object, not a JSON object. – Amadan Commented Oct 2, 2016 at 23:39 - look into using Object.keys() – charlietfl Commented Oct 2, 2016 at 23:44
- @Amadan You're right, thanks. – Jeff Commented Oct 2, 2016 at 23:44
6 Answers
Reset to default 2This is an example of how to iterate through unknown keys
var key;
for (key in arr) {
if (arr.hasOwnProperty(key)) {
console.log(key);
console.log(arr[key]);
}
}
Lodash has some useful function for doing this sort of thing.
_.get, _.set, _.unset
So if you store the node as string form eg. -> a.b.c[0].k, these 3 functions should be able to do what you want.
If you are using JQuery, use the .each() function:
$.each(json,function(key,val){
//You may use key/val for every iteration
});
In order to update or delete, you need to get the parent object and the last key:
var lastKey = keys.pop();
var parentObj = getNodeByKeys(keys); // refactor your code to make this function
parentObj[lastKey] = newValue;
delete parentObj[lastKey];
Get the data via XHR and parse JSON:
var getJSON = function(url) {
return new Promise(function(resolve, reject) {
var xhr = new XMLHttpRequest();
xhr.open('get', url, true);
xhr.onload = function() {
var status = xhr.status;
if (status == 200) {
resolve(JSON.parse(xhr.response));
} else {
reject(status);
}
};
xhr.send();
});
};
then use jQuery each
:
getJSON('//yoursite./yourfile.json').then(function(data) {
$.each(data, function(k, v) {
console.log(k + ', ' + v);
});
}, function(status) {
console.log(status);
});
You can get data from a "path" using this function:
/**
* Get a node from an object according to the given path.
* @param {String} path Node's path.
* @param {Object} data Object to retrieve the desired information.
* @returns {Object} Returns the value from the node, or null in the
* case the node is not found.
*/
function getNode(path, data)
{
var currentNode = data;
path.replace(/^\/|\/$/g, '').split('/').forEach(function(key){
if(key in currentNode)
{
currentNode = currentNode[key];
}
else
{
currentNode = null;
return false;
}
});
return currentNode;
}
From there you could manipulate your object like this:
var myData = {
"key1": {
"innerKey1": {
"innerKey2" : {
"innerKey3": "value1",
"innerKey4": "value2"
}
},
"innerKey5": {
"innerKey6": "value1"
}
},
"key2": "value3",
"key3": "value4"
};
var someNode = getNode('/key1/innerKey5', myData);
// add value
someNode.innerKey7 = 'newValue';
// update existing value
someNode.innerKey7 = 'otherValue';
// delete value
delete someNode.innerKey6;
console.log(myData);