boogy
v1.2.1
Published
Compare objects and check if they are equal according to a recursive equality algorithm. Similiar to NodeJS core module deepEqual in loose mode
Downloads
47
Maintainers
Readme
Boogy
Boogy
is a module which you can use to determine if two objects are equal - either shallow or deep - to each others.
It offers two modes - loose
and strict
, and the loose mode
is somewhat similar to the deepEqual
algoithm found in the
NodeJS
core assert module.
This module is designed to fix all known bugs found in various deepEqual
algorithms online, and support everything
that is possible to support. ES2015
and ES2016
included.
ES2017
is still at the draft stage, but will be supported continuously.
It's safe to use this module in production - over 380 tests (not included subtests) proves that Boogy
is battle tested.
Features
- 100% reliable
- 100% NodeJS core assert module compatible in
loose
mode - ES2016 and ES2017 (still draft) support in
strict
mode - Equal support for
NodeJS 4.x
andNodeJS 6.x
- unlikeNodeJS core assert module
- Follows ECMA standards
- Handle complex datasets
- Supports 2 different modes -
loose
andstrict
- RegExp equality checks are extended to also support
sticky
andunicode
. - High performance
- 37% faster then native
NodejS
solution.
Compatibility
- NodeJS 4.0+
Install
$ npm install --save boogy
Then in your project...
// Node 5.x or newer.
var { strict, loose } = require('boogy');
or
import { strict, loose } from 'boogy';
API
Boogy let you import two different functions, so you can choose between either strict
and loose
mode when you include this module into your project.
Each of the functions takes two arguments of any type, and returns a boolean result. Primitive types are equal if they are ===
.
While composite types, i.e. Objects
and Arrays
, are considered equal if they have both the same structure and each sub-value is also equal.
Circular references in composite structures are supported.
loose(actual, expected)
actual
- Value to compare againstactual
expected
- Value to compare againstexpected
Returns: Boolean indicating whether or not actual
is the same as expected
.
Same for strict
mode.
Differences between loose and strict mode
The differences between loose
and strict
mode are mainly the use of tripple equals. And also that the strict mode does a deeply nested sameValue
equality between two objects of any type, and performs a SameValueZero
comparison
between two values to determine if they are equivalent.
loose({}, []) // => true
strict({}, []) // => false
loose({ 0: 'a', 1: 'b' }, ['a', 'b']) // => true
strict({ 0: 'a', 1: 'b' }, ['a', 'b']) // => false
loose(1, '1') // => true
strict(1, '1') // => false
Differences between Boogy and NodejS core assert module
The core assert module are basicly using ==
for all equality checks, wich include a complicated logic for type conversion that
often can lead to bugs, or give you results you wouldn't expect.
Boogy's loose mode is approximately 100% compatible with the NodejS core assert module
except there is
a small deviation in some areas where current code is either enhanced or extended.
This is done to avoid giving you unexpected results, or encounter bugs. The loose mode also supports Features that isn't supported in the core assert module, and some features that only works for NodeJS 6.x such as TypedArray.prototype.subarray() is also working with NodeJS 4.x with Boogy.
Here are a few strange results that is kept as is in Boogy:
loose([1], true) // => true
loose('0', false) // => true
loose([[]], false) // => true
loose([], false) // => true
loose([], {}) // => true
loose(new Buffer('abc'), new Buffer('xyz')) // => true
loose('\r\n\t', 0) // => true
With Boogys strict mode
this strange behaviour are non-existent - one of the main purposes with the strict mode.
Boogy vs. other deepEqual algorithms
The differences between Boogy and other similiar algorithms are too many that I can list them all here,
but basicly Boogy is a better algorithm that fixes all flaws in similar algorithms, and also have build
in support for the new ES2015
collection. And ES2016
support soon to come.
Around 37% of all tests for this module will fail with other algorithms.
The bugs found in similar modules are mostly related to circular references - and RegExp
. Or
[] === {}
wich returns true. However this is what the NodejS Core assert module
does as well. And
the same behaviour have Boogy
adopted in loose
mode.
AVA
wich using the not-so-shallow
module doesn't have the mentioned issues, but still have it's own
issues. One obvious issue is this:
Error('a') === Error('b') // => true
And the Chai library
have some "really nice bugs" related to circular references, and also this strange behavior:
var symbol1 = Symbol('x');
expect(symbol1, Object(symbol1)).to.be.false; // => TypeError: Cannot convert a Symbol value to a string
vs. Boogy
loose(symbol1, Object(symbol1); // => false
Some examples
Same structure:
loose({ a : [ 2, 3 ], b : [ 4 ] }, { a : [ 2, 3 ], b : [ 4 ] }) // => true
strict({ a : [ 2, 3 ], b : [ 4 ] }, { a : [ 2, 3 ], b : [ 4 ] }) // => true
Different structure:
loose({ x : 2016, y : [2017] }, { x : 2016}) // => false
struct({ x : 2016, y : [2017] }, { x : 2016}) // => false
Same structure, different values:
loose( { x : 2016, y : [6] }, { x : 2017}) // => false
strict( { x : 2016, y : [6] }, { x : 2017}) // => false
Primitives:
loose({ x : 5, y : [6] },{ x : 5}) // => false
strict({ x : 5, y : [6] },{ x : 5}) // => false
ECMA:
loose(function() {}, () => {}) // => false
strict(function() {}, () => {}) // => false
Mixed
loose(a, 'b') // false
loose({a: 0}, {a: '0'}, 'strict') // false
loose({a: 1}, {a: 1}) // true
loose({a: 1, b: 2}, {b: 2, a: 1}) // true
// Both of this will return true in the NodejS core module
loose(Error('a'), Error('a')) // true
loose(Error('a'), Error('b')) // false
strict(Error('a'), Error('b')) // false
let s = Symbol();
loose(s, s); // true
Bugs?
If you find any bugs, feel free to open an issue ticket.
Contribution
You are welcome to contribute at any time :)