Testing Objects Equality In Nodejs
Solution 1:
Node has the built in assert module meant for testing. This has a method called deepEqual for deep equality checking.
Function signature is:
assert.deepEqual(actual, expected, [message])
Quickly written function for testing deepEquality and returning diff:
// Will test own properties onlyfunctiondeepEqualWithDiff(a, e, names){
var dif = {};
var aKeys = Object.keys(a);
var eKeys = Object.keys(e);
var cKeys = aKeys;
var dKeys = eKeys;
var c = a;
var d = e;
var names = {
c: names ? names['a'] : 'Actual',
d: names ? names['e'] : 'Expected'
}
if(eKeys.length > aKeys.length){
cKeys = eKeys;
dKeys = aKeys;
c = e;
d = a;
names = {
d: names ? names['a'] : 'Actual',
c: names ? names['e'] : 'Expected'
}
}
for(var i = 0, co = cKeys.length; i < co; i++){
var key = cKeys[i];
if(typeof c[key] !== typeof d[key]){
dif[key] = 'Type mismatch ' + names['c'] + ':' + typeof c[key] + '!==' + names['d'] + typeof d[key];
continue;
}
if(typeof c[key] === 'function'){
if(c[key].toString() !== d[key].toString()){
dif[key] = 'Differing functions';
}
continue;
}
if(typeof c[key] === 'object'){
if(c[key].length !== undefined){ // arrayvar temp = c[key].slice(0);
temp = temp.filter(function(el){
return (d[key].indexOf(el) === -1);
});
var message = '';
if(temp.length > 0){
message += names['c'] + ' excess ' + JSON.stringify(temp);
}
temp = d[key].slice(0);
temp = temp.filter(function(el){
return (c[key].indexOf(el) === -1);
});
if(temp.length > 0){
message += ' and ' + names['d'] + ' excess ' + JSON.stringify(temp);
}
if(message !== ''){
dif[key] = message;
}
continue;
}
var diff = deepEqualWithDiff(c[key], d[key], {a:names['c'],e:names['d']});
if(diff !== true && Object.keys(diff).length > 0){
dif[key] = diff;
}
continue;
}
// Simple types left soif(c[key] !== d[key]){
dif[key] = names['c'] + ':' + c[key] + ' !== ' + names['d'] + ':' + d[key];
}
}
returnObject.keys(dif).length > 0 ? dif : true;
}
Solution 2:
JavaScript doesn't support object deep equality out of the box and I am not aware of anything built into the NodeJS API either.
My bet would probably be Underscore and the isEqual function.
npm install underscore
var _ = require('underscore');
var moe = {name : 'moe', luckyNumbers : [13, 27, 34]};
varclone = {name : 'moe', luckyNumbers : [13, 27, 34]};
moe == clone;
=> false
_.isEqual(moe, clone);
=> true
Although most Node testing frameworks should also contain an object deep equality assertion but you didn't mention which one you are using.
Solution 3:
deep-diff does what OP is asking for. It can compare two javascript objects / JSON objects and list the differences in a way that your code can access.
This is an old question so this library probably didn't exist at the time the question was asked.
Solution 4:
Note that Node's deepEqual()
is deprecated since Node.js v9.9.0, use deepStrictEqual() instead:
const assert = require('assert');
constactual = {
a: {
name: 'some',
b: {
name: 'thing',
},
},
};
const expected = {
a: {
name: 'thing',
b: {
name: 'some',
},
},
};
assert.deepStrictEqual(actual, expected, 'Expect names to be equal.');
Pro Tip: If you don't use a custom message in deepStrictEqual
, you will get a nice colorful output of the differences between the two objects:
Solution 5:
While I think the basics of object comparison have already been covered (see here and others), if you're looking for a quick and dirty way to execute these tests and see the diff between two non-equal objects, you can just run your tests using nodeunit within the Webstorm IDE (here)
Webstorm integrates particularly well with nodeunit, and for any test.equals() or test.deepEquals() assertions it provides a viewable diff with highlighting to show your descrepencies. I highly recommend the IDE for how well it integrates testing into my js development cycle.
Now, if you need the results of that test/diff to be accessible within your code, this obviously isn't enough for you and I'd recommend copying a couple of the deepEquals comparators from the first link I listed.
Good luck,
Brian
Post a Comment for "Testing Objects Equality In Nodejs"