; | |
const { ARRAY, FUNCTION, NULL, OBJECT } = require('./types.js'); | |
const { isArray, reviver, obj } = require('./utils.js'); | |
(m => { | |
exports.bound = m.bound; | |
exports.unbound = m.unbound; | |
})(require('./utils.js')); | |
/** | |
* @template V | |
* @typedef {import("./utils.js").Arr<V>} Arr | |
*/ | |
/** | |
* @template T, V | |
* @typedef {import("./utils.js").Obj<T, V>} Obj | |
*/ | |
/** | |
* @template V | |
* @typedef {import("./utils.js").TypeOf<V>} TypeOf | |
*/ | |
/** | |
* @template W, T, V | |
* @typedef {W extends Function ? W : W extends Arr<V> ? W[0] : W extends Obj<T, V> ? W["v"] : never} ValueOf | |
*/ | |
/** | |
* @template {string} T | |
* @template V | |
* @param {T} type | |
* @param {V} value | |
* @returns {T extends typeof ARRAY ? Arr<V> : Obj<T, V>} | |
*/ | |
const target = (type, value) => | |
// @see https://github.com/microsoft/TypeScript/issues/33014 | |
// @ts-ignore | |
( | |
type === ARRAY ? | |
(/** @type {Arr<V>} */ ([value])) : | |
obj(type, value) | |
); | |
exports.target = target; | |
/** | |
* @template W, T, V | |
* @param {W} wrap | |
* @param {typeof reviver} [revive] | |
* @returns | |
*/ | |
const unwrap = (wrap, revive = reviver) => { | |
/** @type {string} */ | |
let type = typeof wrap, value = wrap; | |
if (type === OBJECT) { | |
if (isArray(wrap)) { | |
type = ARRAY; | |
value = wrap.at(0); | |
} | |
else | |
({ t: type, v: value } = /** @type {Obj<string, any>} */ (wrap)); | |
} | |
return revive(type, /** @type {ValueOf<W, T, V>} */ (value)); | |
}; | |
exports.unwrap = unwrap; | |
const resolver = (type, value) => ( | |
type === FUNCTION ? value : target(type, value) | |
); | |
/** | |
* @template V | |
* @param {V} value | |
* @param {Function} [resolve] | |
* @returns {V extends Function ? V : V extends Array ? Arr<V> : Obj<TypeOf<V>, V>} | |
*/ | |
const wrap = (value, resolve = resolver) => { | |
const type = value === null ? NULL : typeof value; | |
return resolve(type === OBJECT && isArray(value) ? ARRAY : type, value); | |
}; | |
exports.wrap = wrap; | |