UNPKG

smart-json-diff

Version:

A modern, compact JSON comparison library with path-aware output and multiple output modes

67 lines (66 loc) 2.46 kB
"use strict"; Object.defineProperty(exports, "__esModule", { value: true }); exports.smartJsonDiff = smartJsonDiff; const utils_1 = require("./utils"); function smartJsonDiff(a, b, options = {}) { const { output = 'array', onChange, filterPath, compareArraysByIndex = true, strict = true } = options; const results = []; function compare(objA, objB, path = '') { if (strict ? objA === objB : objA == objB) { return; } if (objA === null || objB === null || objA === undefined || objB === undefined) { if (objA !== objB) { if (!filterPath || filterPath(path)) { results.push({ path, old: objA, new: objB }); } } return; } if (typeof objA === 'function' || typeof objB === 'function' || typeof objA === 'symbol' || typeof objB === 'symbol') { return; } if (typeof objA !== typeof objB) { if (!filterPath || filterPath(path)) { results.push({ path, old: objA, new: objB }); } return; } if ((0, utils_1.isObject)(objA) && (0, utils_1.isObject)(objB)) { const allKeys = new Set([...Object.keys(objA), ...Object.keys(objB)]); for (const key of allKeys) { const newPath = path ? `${path}.${key}` : key; compare(objA[key], objB[key], newPath); } } else if (Array.isArray(objA) && Array.isArray(objB)) { if (compareArraysByIndex) { const maxLength = Math.max(objA.length, objB.length); for (let i = 0; i < maxLength; i++) { const newPath = `${path}[${i}]`; compare(objA[i], objB[i], newPath); } } } else if (objA !== objB) { if (!filterPath || filterPath(path)) { results.push({ path, old: objA, new: objB }); } } } compare(a, b); if (output === 'callback' && onChange) { results.forEach(({ path, old, new: newVal }) => { onChange(path, old, newVal); }); return; } if (output === 'object') { const objectResult = {}; results.forEach(({ path, old, new: newVal }) => { objectResult[path] = { old, new: newVal }; }); return objectResult; } return results; }