Comparing version 1.0.1 to 2.0.0-alpha.1
# Changelog | ||
* `2.0.0-alpha.1`: Use `JSON.stringify()` for all serializations (2x faster than before!) | ||
* `1.0.1`: Fix the delimeter problem once and for all! (see issue #7) | ||
@@ -3,0 +4,0 @@ * `1.0.0`: Fix hash collision cases (see issue #6) |
60
index.js
@@ -5,8 +5,22 @@ 'use strict' | ||
// Delimeter to separate object items form each other | ||
// when stringifying | ||
const DELIM = '\u0000' | ||
function _serialize (obj) { | ||
if (Array.isArray(obj)) { | ||
for (let i = 0; i < obj.length; i++) { | ||
obj[i] = _serialize(obj[i]) | ||
} | ||
return obj | ||
} else if (typeof obj === 'object' && obj != null) { | ||
const sortedKeys = Object.keys(obj).sort() | ||
for (let i = 0; i < sortedKeys.length; i++) { | ||
const k = sortedKeys[i] | ||
obj[k] = _serialize(obj[k]) | ||
} | ||
return JSON.stringify(obj, sortedKeys) | ||
} | ||
return obj | ||
} | ||
/** | ||
* Stringifies a JSON object (not any randon JS object). | ||
* Serializes a JSON object (not any random JS object). | ||
* | ||
@@ -20,26 +34,5 @@ * It should be noted that JS objects can have members of | ||
*/ | ||
function stringify (obj) { | ||
if (Array.isArray(obj)) { | ||
let stringifiedArr = [] | ||
for (let i = 0; i < obj.length; i++) { | ||
stringifiedArr[i] = stringify(obj[i]) | ||
} | ||
return JSON.stringify(stringifiedArr) | ||
} else if (typeof obj === 'object' && obj !== null) { | ||
let acc = [] | ||
let sortedKeys = Object.keys(obj).sort() | ||
for (let i = 0; i < sortedKeys.length; i++) { | ||
let k = sortedKeys[i] | ||
acc[i] = `${k}:${stringify(obj[k])}` | ||
} | ||
return acc.join(DELIM) | ||
} else if (typeof obj === 'string') { | ||
// See issue #6 for details | ||
return `"${obj}"` | ||
} | ||
return obj | ||
function serialize (obj) { | ||
const ser = _serialize(obj) | ||
return (typeof ser !== 'string') ? JSON.stringify(ser) : ser | ||
} | ||
@@ -53,12 +46,15 @@ | ||
* @param {String} encoding hash encoding (e.g. base64) or none for buffer | ||
* @see #stringify | ||
* @see #serialize | ||
*/ | ||
function digest (obj, hashAlgorithm, encoding) { | ||
let hash = crypto.createHash(hashAlgorithm) | ||
return hash.update(stringify(obj)).digest(encoding) | ||
const hash = crypto.createHash(hashAlgorithm) | ||
return hash.update(serialize(obj)).digest(encoding) | ||
} | ||
module.exports = { | ||
stringify: stringify, | ||
stringify: () => { | ||
throw new Error('"stringify()" is deprecated, use "serialize()" instead!') | ||
}, | ||
serialize: serialize, | ||
digest: digest | ||
} |
{ | ||
"name": "jsum", | ||
"version": "1.0.1", | ||
"version": "2.0.0-alpha.1", | ||
"description": "Consistent checksum calculation of JSON objects.", | ||
@@ -5,0 +5,0 @@ "main": "index.js", |
@@ -13,4 +13,4 @@ # JSum | ||
console.log(JSum.digest(obj1, 'SHA256', 'hex')) // 7514a2664dab82189b89d8250da9d0e1e6c95d3efaca6ffc25e5db42d7a7d053 | ||
console.log(JSum.digest(obj2, 'SHA256', 'hex')) // 7514a2664dab82189b89d8250da9d0e1e6c95d3efaca6ffc25e5db42d7a7d053 | ||
console.log(JSum.digest(obj1, 'SHA256', 'hex')) // 9a08ad6302b1e9e5682c365c8b24c5ca2ea6db5c90b672bc5b579879136dda0c | ||
console.log(JSum.digest(obj2, 'SHA256', 'hex')) // 9a08ad6302b1e9e5682c365c8b24c5ca2ea6db5c90b672bc5b579879136dda0c | ||
``` | ||
@@ -44,3 +44,3 @@ | ||
| `json-stable-stringify` | `12134` | | ||
| `JSum` | `9656` | | ||
| `JSum` | `7200` | | ||
| `json-checksum` | `FATAL ERROR: [...] - process out of memory` | | ||
@@ -69,7 +69,7 @@ | ||
# benchmark/fixtures/medium.json (77986 bytes) | ||
fast-json-stable-stringify x 645 ops/sec ±0.80% (86 runs sampled) | ||
json-checksum x 228 ops/sec ±0.89% (82 runs sampled) | ||
json-hash x 70.25 ops/sec ±1.89% (60 runs sampled) | ||
json-stable-stringify x 601 ops/sec ±1.06% (86 runs sampled) | ||
jsum x 1,196 ops/sec ±1.08% (85 runs sampled) | ||
fast-json-stable-stringify x 629 ops/sec ±1.67% (81 runs sampled) | ||
json-checksum x 236 ops/sec ±0.88% (82 runs sampled) | ||
json-hash x 83.40 ops/sec ±1.25% (60 runs sampled) | ||
json-stable-stringify x 609 ops/sec ±0.80% (87 runs sampled) | ||
jsum x 1,118 ops/sec ±0.68% (89 runs sampled) | ||
@@ -79,41 +79,9 @@ fastest is jsum | ||
# benchmark/fixtures/small.json (456 bytes) | ||
fast-json-stable-stringify x 64,153 ops/sec ±1.47% (88 runs sampled) | ||
json-checksum x 20,089 ops/sec ±1.88% (87 runs sampled) | ||
json-hash x 6,418 ops/sec ±2.13% (75 runs sampled) | ||
json-stable-stringify x 52,923 ops/sec ±1.91% (89 runs sampled) | ||
jsum x 89,836 ops/sec ±0.84% (88 runs sampled) | ||
fast-json-stable-stringify x 67,381 ops/sec ±1.16% (84 runs sampled) | ||
json-checksum x 21,372 ops/sec ±1.21% (89 runs sampled) | ||
json-hash x 7,409 ops/sec ±1.17% (75 runs sampled) | ||
json-stable-stringify x 54,015 ops/sec ±0.89% (83 runs sampled) | ||
jsum x 90,816 ops/sec ±1.06% (87 runs sampled) | ||
fastest is jsum | ||
``` | ||
## I don't want this :-( | ||
Fair enough! Just copy (check the license first!) this for your own code and hash as you will: | ||
```js | ||
/** | ||
* Stringifies a JSON object (not any randon JS object). | ||
* | ||
* It should be noted that JS objects can have members of | ||
* specific type (e.g. function), that are not supported | ||
* by JSON. | ||
* | ||
* @param {Object} obj JSON object | ||
* @returns {String} stringified JSON object. | ||
*/ | ||
function serialize (obj) { | ||
if (Array.isArray(obj)) { | ||
return JSON.stringify(obj.map(i => serialize(i))) | ||
} else if(typeof obj === 'string') { | ||
return `"${obj}"` | ||
} else if (typeof obj === 'object' && obj !== null) { | ||
return Object.keys(obj) | ||
.sort() | ||
.map(k => `${k}:${serialize(obj[k])}`) | ||
.join('|') | ||
} | ||
return obj | ||
} | ||
``` | ||
***NOTE***: this code is slightly inferior in terms of performance comparing to module's implementation. |
License Policy Violation
LicenseThis package is not allowed per your license policy. Review the package's license to ensure compliance.
Found 1 instance in 1 package
No v1
QualityPackage is not semver >=1. This means it is not stable and does not support ^ ranges.
Found 1 instance in 1 package
License Policy Violation
LicenseThis package is not allowed per your license policy. Review the package's license to ensure compliance.
Found 1 instance in 1 package
7
67
40186
2
84