UNPKG

zexson_toolkit

Version:

Zexson Toolkit is a powerful encryption and tokenization library developed by Zexson Team. It offers proprietary encryption algorithms, high-security random token generation, and advanced object comparison features. It includes many advanced security func

111 lines (110 loc) 4.55 kB
"use strict"; Object.defineProperty(exports, "__esModule", { value: true }); exports.isEquals = void 0; /** * Deeply compares two objects or arrays for equality, with optional type checking. * * @template T - Generic type extending Record<string, any> * @param {T} obj1 - First object to compare * @param {T} obj2 - Second object to compare * @param {CompareOptions} [options={ checkType: false }] - Comparison options * @param {boolean} options.checkType - When true, compares types instead of values * @returns {boolean} Returns true if objects are equal based on comparison criteria * * @example * // Compare values * const obj1 = { name: "John", age: 30, details: { city: "New York" } } * const obj2 = { name: "John", age: 30, details: { city: "New York" } } * isEqualsObject(obj1, obj2) // true * * // Compare types * const obj3 = { name: "John", age: 25 } * const obj4 = { name: "Jane", age: 30 } * isEqualsObject(obj3, obj4, { checkType: true }) // true * * @since 1.1.2 * @category Comparison * @public */ const isEquals = (obj1, obj2, options = { checkType: false }) => { if (!obj2 && options.schema && obj1) return validateSchema(obj1, options.schema); if (options.schema) { options.checkType = true; const schemaValid = validateSchema(obj1, options.schema) && validateSchema(obj2, options.schema); if (!schemaValid) return false; } if (typeof obj1 !== 'object' || typeof obj2 !== 'object') return options.checkType ? typeof obj1 === typeof obj2 : obj1 === obj2; if (obj1 === null || obj2 === null) return options.checkType ? typeof obj1 === typeof obj2 : obj1 === obj2; if (Array.isArray(obj1) && Array.isArray(obj2)) { if (obj1.length !== obj2.length) return false; return obj1.every((item, index) => (0, exports.isEquals)(item, obj2[index], options)); } if ((typeof obj1 == 'object' && typeof obj2 == 'object')) { if ((!Array.isArray(obj1) && Array.isArray(obj2))) return false; if (Array.isArray(obj1) && !Array.isArray(obj2)) return false; } const keys1 = Object.keys(obj1), keys2 = Object.keys(obj2); if (keys1.length !== keys2.length) return false; return keys1.every(key => { if (!obj2.hasOwnProperty(key)) return false; return (0, exports.isEquals)(obj1[key], obj2[key], options); }); }; exports.isEquals = isEquals; function validateSchema(obj, schema) { const schemaKeys = Object.keys(schema), objKeys = Object.keys(obj); if (schemaKeys.length !== objKeys.length) return false; if (!schemaKeys.every(key => objKeys.includes(key))) return false; for (const [key, schemaType] of Object.entries(schema)) { const value = obj[key]; if (typeof schemaType === 'string') { if (typeof value !== schemaType) return false; } else if (typeof schemaType === 'object' && 'type' in schemaType) { if (schemaType.type === 'array') { if (!Array.isArray(value)) return false; if (schemaType.items) { if (!value.every(item => { if (schemaType.items?.type === 'string' && schemaType.items.enum) return schemaType.items.enum.includes(item); return validateValue(item, schemaType.items); })) return false; } if (schemaType.enum) if (!value.every(item => schemaType.enum.includes(item))) return false; } if (schemaType.enum) if (!schemaType.enum.includes(value)) return false; if (schemaType.type === 'object' && schemaType.properties) { if (typeof value !== 'object' || value === null) return false; if (!validateSchema(value, schemaType.properties)) return false; } } } return true; } function validateValue(value, schemaType) { if (typeof schemaType === 'string') return typeof value === schemaType; if (Array.isArray(schemaType)) return schemaType.includes(value); return validateSchema({ value }, { value: schemaType }); }