UNPKG

utils-data

Version:

Utilities for various data type validations, comparisons and an advanced "stringify".

197 lines (184 loc) 7.07 kB
/** * Created by Shyam on 1/23/2018. */ /** * Utilities for various data type validations, comparisons and an advanced "stringify". */ var Utilities = { isStr: function (str) { return str && (typeof str === "string" || str instanceof String); }, isValidStr: function (str) { return Utilities.isStr(str) && str.trim().length; }, isNumeric: function (n) { return !isNaN(parseFloat(n)) && isFinite(n); }, isValidArray: function (arr) { return arr && Array.isArray(arr) && arr.length; }, isFunction: function (fn) { return fn && (typeof fn === "function" || fn instanceof Function); }, /** * Checks whether the given value is a JSON or not. * * @param {*} v The value to be checked if JSON or not. * @param {boolean} [failIfHasFunctions] If true, the * check will fail if the JSON contains functions. * @returns {boolean} */ isJSON: function (v, failIfHasFunctions) { // Object, string and arrays have keys. var isJSON = v && Object.keys(v).length > 0 && !Array.isArray(v) && typeof v !== 'string' && !(v instanceof String); if (!isJSON) { // pass if empty object isJSON = JSON.stringify(v) == "{}"; } else if (failIfHasFunctions) { var pv; var keys = Object.keys(v); for (var i = 0; i < keys.length; ++i) { pv = v[keys[i]]; if (typeof pv === "function") return false; else if (Utilities.isJSON(pv)) return Utilities.isJSON(pv, true); } } return isJSON; }, /** * Checks whether the two are RegExps and are equal or not. * * @param r1 * @param r2 * @returns {boolean} */ areRegExpsSame: function (r1, r2) { return r1 instanceof RegExp && r2 instanceof RegExp && r1.source === r2.source && r1.global === r2.global && r1.ignoreCase === r2.ignoreCase && r1.multiline === r2.multiline; }, areDatesSame: function (d1, d2) { return d1 instanceof Date && d2 instanceof Date && d1.getTime() == d2.getTime(); }, areOfSameDataTypes: function (v1, v2) { // note: typeof null = "object" return v1 == v2 || (typeof v1 == typeof v2 && (typeof v1 !== "object" || (typeof v1 === "object" && v1 != null && v2 != null && v1.constructor === v2.constructor))); }, /** * Checks whether the array contains the value or not. * * @param {Array} arr * @param {*} value * @returns {boolean} whether the array contains the value or not. */ arrayContainsValue: function (arr, value) { if (!arr.length) return false; // primitive types if (arr.indexOf(value) >= 0) return true; // RegExp|json for (var i = 0; i < arr.length; ++i) { if (Utilities.deepEquals(value, arr[i])) return true; } return false; }, /** * Checks whether the two literals or objects are equal or not. It ignores * the sequence of elements of an array. * * @param {*} o1 * @param {*} o2 * @returns {boolean} whether the two literals or objects are equal or not */ deepEquals: function (o1, o2) { // primitive types, RegExps and Dates if (o1 == o2 || Utilities.areRegExpsSame(o1, o2) || Utilities.areDatesSame(o1, o2)) return true; // if of different data types if (!Utilities.areOfSameDataTypes(o1, o2)) return false; var k1 = Object.keys(o1).sort(); var k2 = Object.keys(o2).sort(); // compare keys if (!k1.length || k1.length != k2.length || k1.join() != k2.join()) return false; for (var i = 0; i < k1.length; ++i) { var o1p = o1[k1[i]]; var o2p = o2[k2[i]]; if (!Utilities.areOfSameDataTypes(o1p, o2p) || (o1p instanceof RegExp && !Utilities.areRegExpsSame(o1p, o2p)) || (o1p instanceof Date && !Utilities.areDatesSame(o1p, o2p)) || (Utilities.isJSON(o1p) && !Utilities.deepEquals(o1p, o2p)) || (!Utilities.isJSON(o1p) && o1p != o2p)) { return false; } } return true; }, /** * A replacement for the inbuilt JSON.stringify() with abilities to print * regexp fields properly, and beautify the output with newlines and indents. * @param {*} v The data to be converted to a string. * @param {boolean} [beautify=false] If true, the output string of a JSON * will be formatted using newlines and indents. * @param {string} [indent=""] Additional indentation for the JSON output. * @param {string} [indentChar="\t"] Indent character. Default is TAB. * @returns {string} */ JSONstringify: function (v, beautify, indent, indentChar) { var nextIndent; if (beautify) { indent = indent || ""; indentChar = indentChar || "\t"; nextIndent = indent + indentChar; } var out = ""; var i; if (typeof v == "number") { out += v; } else if (v instanceof RegExp) { out += v.toString(); } else if (Array.isArray(v)) { out += "["; if (beautify && v.length > 1) { out += "\n" + nextIndent; } for (i = 0; i < v.length; ++i) { if (i > 0) { out += ","; if (beautify) { out += "\n" + nextIndent; } } out += Utilities.JSONstringify(v[i], beautify, v.length > 1 ? nextIndent : indent, indentChar); } if (beautify && v.length > 1) out += "\n" + indent; out += "]"; } else if (Utilities.isJSON(v)) { out += "{"; var keys = Object.keys(v); if (beautify && keys.length > 1) out += "\n" + nextIndent; for (i = 0; i < keys.length; ++i) { if (i > 0) { out += ","; if (beautify) out += "\n" + nextIndent; } out += JSON.stringify(keys[i]) + (beautify ? ": " : ":") + Utilities.JSONstringify(v[keys[i]], beautify, keys.length > 1 ? nextIndent : indent, indentChar); } if (beautify && keys.length > 1) out += "\n" + indent; out += "}"; } else if (v && Utilities.isFunction(v.toString)) { // convert to string out += JSON.stringify(v.toString()); } else { out += JSON.stringify(v); } return out; } }; module.exports = Utilities;