Last active
January 4, 2016 13:59
-
-
Save pinalbhatt/8631102 to your computer and use it in GitHub Desktop.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
/* | |
Javascript | |
ResolveReferences - To resolve references in JSON object with circular references. | |
*/ | |
function ResolveReferences(json) { | |
if (typeof json === 'string') | |
json = JSON.parse(json); | |
var byid = {}, // all objects by id | |
refs = []; // references to objects that could not be resolved | |
json = (function recurse(obj, prop, parent) { | |
if (typeof obj !== 'object' || !obj) // a primitive value | |
return obj; | |
if (Object.prototype.toString.call(obj) === '[object Array]') { | |
for (var i = 0; i < obj.length; i++) | |
if ("$ref" in obj[i]) | |
obj[i] = recurse(obj[i], i, obj); | |
else | |
obj[i] = recurse(obj[i], prop, obj); | |
return obj; | |
} | |
if ("$ref" in obj) { // a reference | |
var ref = obj.$ref; | |
if (ref in byid) | |
return byid[ref]; | |
// else we have to make it lazy: | |
refs.push([parent, prop, ref]); | |
return; | |
} else if ("$id" in obj) { | |
var id = obj.$id; | |
delete obj.$id; | |
if ("$values" in obj) // an array | |
obj = obj.$values.map(recurse); | |
else // a plain object | |
for (var prop in obj) | |
obj[prop] = recurse(obj[prop], prop, obj); | |
byid[id] = obj; | |
} | |
return obj; | |
})(json); // run it! | |
for (var i = 0; i < refs.length; i++) { // resolve previously unknown references | |
var ref = refs[i]; | |
ref[0][ref[1]] = byid[ref[2]]; | |
// Notice that this throws if you put in a reference at top-level | |
} | |
return json; | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment