UNPKG

super-utils-plus

Version:

A superior alternative to Lodash with improved performance, TypeScript support, and developer experience

124 lines (123 loc) 3.76 kB
/** * Type checking functions with improved TypeScript support */ /** * Checks if value is null or undefined */ export const isNil = (value) => value === null || value === undefined; /** * Checks if value is undefined */ export const isUndefined = (value) => value === undefined; /** * Checks if value is null */ export const isNull = (value) => value === null; /** * Checks if value is a number * Unlike Lodash, this correctly returns false for NaN */ export const isNumber = (value) => typeof value === 'number' && !Number.isNaN(value); /** * Checks if value is a string */ export const isString = (value) => typeof value === 'string'; /** * Checks if value is a boolean */ export const isBoolean = (value) => typeof value === 'boolean'; /** * Checks if value is a function */ // eslint-disable-next-line @typescript-eslint/ban-types export const isFunction = (value) => typeof value === 'function'; /** * Checks if value is an array */ export const isArray = Array.isArray; /** * Checks if value is an object (excluding null) * This is different from Lodash as it doesn't consider arrays as objects */ export const isObject = (value) => value !== null && typeof value === 'object' && !isArray(value); /** * Checks if value is a plain object (created by Object constructor or object literal) */ export const isPlainObject = (value) => { if (value === null || typeof value !== 'object') return false; const proto = Object.getPrototypeOf(value); return proto === null || proto === Object.prototype; }; /** * Checks if value is a Date object */ export const isDate = (value) => value instanceof Date; /** * Checks if value is a RegExp object */ export const isRegExp = (value) => value instanceof RegExp; /** * Checks if value is a valid finite number */ export const isFinite = (value) => isNumber(value) && Number.isFinite(value); /** * Checks if value is an integer */ export const isInteger = (value) => isNumber(value) && Number.isInteger(value); /** * Checks if value is NaN */ export const isNaN = (value) => Number.isNaN(value); /** * Checks if value is empty * Works with strings, arrays, objects, maps, sets */ export const isEmpty = (value) => { if (isNil(value)) return true; if (isString(value) || isArray(value)) return value.length === 0; if (value instanceof Map || value instanceof Set) return value.size === 0; if (isObject(value)) return Object.keys(value).length === 0; return false; }; /** * Checks if two values are equal (deep comparison) */ export const isEqual = (value, other) => { // Same reference or both NaN if (value === other || (isNaN(value) && isNaN(other))) return true; // Different types or null/undefined if (isNil(value) || isNil(other) || typeof value !== typeof other) return false; // Compare arrays if (isArray(value) && isArray(other)) { if (value.length !== other.length) return false; return value.every((item, i) => isEqual(item, other[i])); } // Compare dates if (isDate(value) && isDate(other)) { return value.getTime() === other.getTime(); } // Compare regexps if (isRegExp(value) && isRegExp(other)) { return value.toString() === other.toString(); } // Compare objects if (isObject(value) && isObject(other)) { const valueKeys = Object.keys(value); const otherKeys = Object.keys(other); if (valueKeys.length !== otherKeys.length) return false; return valueKeys.every(key => { return Object.prototype.hasOwnProperty.call(other, key) && isEqual(value[key], other[key]); }); } return false; };