json-diff/js/lib/jsond.js
2010-12-07 15:22:24 -05:00

130 lines
3.9 KiB
JavaScript

var jsond = (typeof exports !== "undefined" ? exports : window).jsond = (function(){
function isArray(value) {
return value && typeof value === "object" && value.constructor === Array;
}
function typeofReal(value) {
return isArray(value) ? "array": value === null ? 'null' : typeof value;
}
function getType(value) {
(typeA === "object" || typeA === "array") ? "": String(a) + " ";
}
return {
version: "0.0.1",
a: [], // first structure
b: [], // second structure
feedback: function() {
},
swap: function(fn) {
console.log('>>> swapBoxes()');
this.a = [this.b, this.b = this.a][0];
fn(this.a, this.b);
},
clear: function(fn) {
console.log('>>> clearValues()');
this.a = this.b = {};
fn(this.a, this.b);
},
compare: function(a, b, name, results, fn) {
// To-Do: a and/or b should accept a uri or a json structure.
// To-Do: this DOM manipulation should be seperated into logic and rendering so that it works with nodejs.
var self = this;
var typeA = typeofReal(a);
var typeB = typeofReal(b);
console.log('>>> compare(a=(', typeA, ')', a,
', b=(', typeB, ')', b,
', name=(', typeof name, ')', name,
', results=(', typeof results, ')', results, ')');
var typeSpanA = document.createElement("span");
typeSpanA.appendChild(document.createTextNode("(" + typeA + ")"))
typeSpanA.setAttribute("class", "typeName");
var typeSpanB = document.createElement("span");
typeSpanB.appendChild(document.createTextNode("(" + typeB + ")"))
typeSpanB.setAttribute("class", "typeName");
var aString = (typeA === "object" || typeA === "array") ? "": String(a) + " ";
var bString = (typeB === "object" || typeB === "array") ? "": String(b) + " ";
var leafNode = document.createElement("span");
leafNode.appendChild(document.createTextNode(name));
if (a === undefined)
{
leafNode.setAttribute("class", "added");
leafNode.appendChild(document.createTextNode(": " + bString));
leafNode.appendChild(typeSpanB);
self.feedback(leafNode);
}
else if (b === undefined)
{
leafNode.setAttribute("class", "removed");
leafNode.appendChild(document.createTextNode(": " + aString));
leafNode.appendChild(typeSpanA);
self.feedback(leafNode);
}
else if (typeA !== typeB || (typeA !== "object" && typeA !== "array" && a !== b))
{
leafNode.setAttribute("class", "changed");
leafNode.appendChild(document.createTextNode(": " + aString));
leafNode.appendChild(typeSpanA);
leafNode.appendChild(document.createTextNode(" => " + bString));
leafNode.appendChild(typeSpanB);
if (name === 'key') leafNode.setAttribute('class', 'changed key');
else self.feedback(leafNode);
}
else
{
leafNode.appendChild(document.createTextNode(": " + aString));
leafNode.appendChild(typeSpanA);
}
if (typeA === "object" || typeA === "array" || typeB === "object" || typeB === "array")
{
var keys = [];
for (var i in a) keys.push(i);
for (var i in b) keys.push(i);
keys.sort();
var listNode = document.createElement("ul");
listNode.appendChild(leafNode);
for (var i = 0; i < keys.length; i++)
{
if (keys[i] === keys[i - 1])
continue;
var li = document.createElement("li");
listNode.appendChild(li);
self.compare(a && a[keys[i]], b && b[keys[i]], keys[i], li);
}
results.appendChild(listNode);
}
else
{
results.appendChild(leafNode);
}
}
};
})();