Dear @Winkel_Philipp1,
Indeed it looks like a bug, and thank you for the investigation and detailed report. We will fix this for the next release.
In the meanwhile, this is the updated function we will release. If you feel like patching your source code right away, please let me know if it works for you:
procedure TXDataWebClient.SolveReferences(json: JSValue);
asm
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++)
// check also if the array element is not a primitive value
if (typeof obj[i] !== 'object' || !obj[i]) // a primitive value
continue;
else 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 p in obj)
obj[p] = recurse(obj[p], p, obj);
byid[id] = obj;
} else {
// NEW: recurse into plain objects (no $id / $ref),
// e.g. { "value": [ ... ] }
for (var p in obj)
obj[p] = recurse(obj[p], p, 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
}
end;