UNPKG

alwz

Version:

Extendable library for typecasting

337 lines 11 kB
import Converter from './models/Converter.js'; import * as numbers from './constants/numbers.js'; import is, { integers as intIs, floats as floatIs } from './is.js'; /** * @namespace presets */ /** * @memberof presets * @example * boolean.convert('abc'); // true * boolean.convert(Symbol.for('')); // false * boolean.convert([]); // false * boolean.convert([0]); // false * boolean.convert([false, true]); // false * boolean.convert([123]); // true */ export const boolean = new Converter(is.boolean, Boolean) .undefined(Boolean) .number(Boolean) .bigint(Boolean) .string(Boolean) .symbol(function (i) { return this.convert(string.convert(i)); }) .register(is.null, Boolean) .register(is.Array, function (i) { return this.convert(i[0]); }) .register(is.Date, (i) => Boolean(i.getTime())); /** * @memberof presets * @example * number.convert(Infinity); // Infinity * number.convert('42'); // 42 * number.convert('abc'); // NaN * number.convert(Symbol.for('42')); // 42 * number.convert(new Date('1970-01-01T00:00:00.042Z')); // 42 * number.convert(['42']); // 42 * number.convert([ [ [ 42 ] ] ]); // 42 * number.convert(new Date('1970-01-01T00:00:00.999Z')); // 999 */ export const number = new Converter(is.number, Number) .undefined(Number) .boolean(Number) .bigint(Number) .string(Number) .symbol((i) => Number(string.convert(i))) .register(is.null, () => 0) .register(is.Array, function (i) { return this.convert(i[0]); }) .register(is.Date, (i) => i.getTime()); /** * @memberof presets * @name integers * @description * ``` * |--------|------------------|------------------| * | type | min | max | * |--------|------------------|------------------| * | byte | -128 | 127 | * | short | -32768 | 32767 | * | int | -2147483648 | 2147483647 | * | long | MIN_SAFE_INTEGER | MAX_SAFE_INTEGER | * |--------|------------------|------------------| * | ubyte | 0 | 255 | * | ushort | 0 | 65535 | * | uint | 0 | 4294967295 | * | ulong | 0 | MAX_SAFE_INTEGER | * |--------|------------------|------------------| * ``` * @example * int.convert(undefined); // 0 * int.convert(null); // 0 * int.convert(NaN); // 0 * int.convert('abc'); // 0 * int.convert(true); // 1 * int.convert(42.5); // 42 * int.convert('42.5'); // 42 * int.convert(['42.5']); // 42 * int.convert(Symbol.for('42.5')); // 42 * int.convert(new Date('1970-01-01T00:00:00.042Z')); // 42 * int.convert(new Date(NaN)); // 0 */ /** * @memberof presets * @name signed * @description cast to byte, short (2 bytes), int (4 bytes) or long (8 bytes) * @example * byte.convert(128); // 127 * byte.convert(Infinity); // 127 * byte.convert(-Infinity); // -128 * short.convert(Infinity); // 32767 * short.convert(-Infinity); // -32768 * int.convert(Infinity); // 2147483647 * int.convert(-Infinity); // -2147483648 * long.convert(Infinity); // MAX_SAFE_INTEGER * long.convert(-Infinity); // MIN_SAFE_INTEGER */ const numeric = number.clone() .undefined(() => 0) .bigint(function (i) { return this.convert(Number(i)); }) .string(function (i) { return this.convert(Number(i)); }) .symbol(function (i) { return this.convert(string.convert(i)); }) .register(is.Date, function (i) { return this.convert(i.getTime()); }); numeric.fallback = () => 0; /** * @memberof presets * @name unsigned * @description cast to ubyte, ushort (2 bytes), uint (4 bytes) or ulong (8 bytes) * @example * ubyte.convert(-7); // 0 * ubyte.convert('a'); // 0 * ubyte.convert(Infinity); // 255 * ubyte.convert(-Infinity); // 0 * ushort.convert(Infinity); // 65535 * ushort.convert(-Infinity); // 0 * uint.convert(Infinity); // 4294967295 * uint.convert(-Infinity); // 0 * ulong.convert(Infinity); // MAX_SAFE_INTEGER * ulong.convert(-Infinity); // 0 */ export const { byte, short, int, long, ubyte, ushort, uint, ulong, } = Object.fromEntries(Object.entries(numbers.integers) .map(([name, [min, max]]) => { const converter = numeric.clone() .number(function (i) { if (i <= min) { return min; } else if (i >= max) { return max; } else if (Number.isNaN(i)) { return 0; } else { return Math.trunc(i); } }); converter.is = intIs[name]; return [name, converter]; })); /** * @memberof presets * @example * double.convert('42.5'); // 42.5 * double.convert(Infinity); // Number.MAX_VALUE * double.convert(NaN); // 0 */ export const { double, } = Object.fromEntries(Object.entries(numbers.floats) .map(([name, [min, max]]) => { const converter = numeric.clone() .number(function (i) { if (i >= max) { return max; } else if (i <= min) { return min; } else { return 0; } }); converter.is = floatIs[name]; return [name, converter]; })); /** * @memberof presets * @example * bigint.convert(42.5); // 42n * bigint.convert('42'); // 42n * bigint.convert('42.5'); // 0n * bigint.convert(Symbol.for('42')); // 42n * bigint.convert(new Date('1970-01-01T00:00:00.999Z')); // 999n */ export const bigint = new Converter(is.bigint, () => BigInt(0)) .undefined(() => BigInt(0)) .boolean((i) => BigInt(i)) .number((i) => BigInt(Math.trunc(double.convert(i)))) .string(function (i) { return this.convert(Number(i)); }) .symbol(function (i) { return this.convert(string.convert(i)); }) .register(is.null, () => BigInt(0)) .register(is.Array, function (i) { return this.convert(i[0]); }) .register(is.Date, function (i) { return this.convert(i.getTime()); }); /** * @memberof presets * @example * string.convert(); // '' * string.convert(null); // '' * string.convert(false); // '' * string.convert(true); // ' ' * string.convert(42.5); // '42.5' * string.convert([1, 2, 3]); // '1' * string.convert(Symbol.for('42')); // '42' * string.convert(new Date('1970-01-01T00:00:00.999Z')); // '1970-01-01T00:00:00.999Z' */ export const string = new Converter(is.string, String) .undefined(() => '') .boolean((i) => i ? ' ' : '') .number((i) => i === i ? String(i) : '') .bigint(String) .symbol((i) => Symbol.keyFor(i) || '') .register(is.null, () => '') .register(is.Array, function (i) { return this.convert(i[0]); }) .register(is.Date, function (i) { const ts = i.getTime(); if (Number.isFinite(ts)) { return i.toISOString(); } else { return new Date(0).toISOString(); } }); /** * @memberof presets * @example * symbol.convert(false); // Symbol('') * symbol.convert(42.5); // Symbol('42.5') * symbol.convert('42.5'); // Symbol('42.5') * symbol.convert([1.5, 2, 3]); // Symbol('1.5') * symbol.convert(new Date('1970-01-01T00:00:00.999Z')); // Symbol('1970-01-01T00:00:00.999Z') */ export const symbol = new Converter(is.symbol, (i) => Symbol.for(string.convert(i))); /** * @memberof presets * @example * array.convert(); // [] * array.convert(null); // [] * array.convert(false); // [false] * array.convert(123); // [123] * array.convert('1,2,3'); // ['1,2,3'] * array.convert(new Set([1, 2, 3])); // [1, 2, 3] * array.convert(new Map([[1, 2], [3, 4], [5, 6]])); // [[1, 2], [3, 4], [5, 6]] */ export const array = new Converter(is.Array, (i) => ([i])) .undefined(() => []) .boolean((i) => [i]) .number((i) => [i]) .bigint((i) => [i]) .string((i) => [i]) .symbol((i) => [i]) .register(is.null, () => []) .register(is.Iterable, Array.from); /** * @memberof presets * @example * fn.convert((a, b) => a + b); // (a, b) => a + b * fn.convert(123); // () => 123 */ // eslint-disable-next-line no-unused-vars export const fn = new Converter(is.function, (i) => () => i); /** * @memberof presets * @example * date.convert(111); // Date('1970-01-01T00:00:00.111Z') * date.convert([222, 333]); // Date('1970-01-01T00:00:00.222Z') * date.convert('abc'); // Date(NaN) */ export const date = new Converter(is.Date, () => new Date(NaN)) .undefined(() => new Date(NaN)) .boolean((i) => new Date(Number(i))) .number((i) => new Date(i)) .bigint((i) => new Date(Number(i))) .string((i) => new Date(i)) .symbol((i) => new Date(string.convert(i))) .register(is.Array, function (i) { return this.convert(i[0]); }); /** * @memberof presets * @example * object.convert(undefined); // {} * object.convert(null); // {} * object.convert(false); // Boolean { false } * object.convert(1); // Number { 1 } * object.convert('2'); // String { 2 } * object.convert([1, '2', 3n]); // [1, '2', 3n] */ export const object = new Converter(is.object, Object); /** * @memberof presets * @example * map.convert([ [true, 1], 2, '3']); // Map { [true, 1] } */ export const map = new Converter(is.Map, () => new Map()) .register(is.Iterable, (input) => { const result = new Map(); for (const item of input) { if (is.Iterable(item)) { const [key, value] = item; result.set(key, value); } } return result; }); /** * @memberof presets * @example * weakmap.convert([ [Boolean, 'bool'], [Number, 'num'], [String, 'str'], [true, 1], 2, '3']); // WeakMap { [Boolean, 'bool'], [Number, 'num'], [String, 'str'] } */ export const weakmap = new Converter(is.WeakMap, () => new WeakMap()) .register(is.Iterable, (input) => { const result = new WeakMap(); for (const item of input) { if (is.Iterable(item)) { const [key, value] = item; if ((typeof key === 'object' && key !== null) || typeof key === 'function') { result.set(key, value); } } } return result; }); /** * @memberof presets * @example * set.convert([1, '2', 3]); // Set {1, '2', 3} */ export const set = new Converter(is.Set, (i) => new Set().add(i)) .undefined(() => new Set()) .register(is.null, () => new Set()) .register(is.Iterable, (i) => new Set(i)); /** * @memberof presets * @example * weakset.convert([Boolean, Number, String, true, 2, '3']); // WeakSet { Boolean, Number, String } */ export const weakset = new Converter(is.WeakSet, () => new WeakSet()) .register(is.Iterable, (i) => { const result = new WeakSet(); for (const item of i) { if ((typeof item === 'object' && item !== null) || typeof item === 'function') { result.add(item); } } return result; }); /** * @memberof presets * @example * promise.convert(Promise.resolve(1)); // Promise { 1 } * promise.convert(42); // Promise { 42 } */ export const promise = new Converter(is.Promise, (i) => Promise.resolve(i)); //# sourceMappingURL=presets.js.map