UNPKG

typing-assets

Version:

Additional typing assets and helpers for better TypeScript experience

110 lines (98 loc) 3.87 kB
/** * @description Checks types of borrowed variables list * @param args List of values * @returns `boolean` - `true` if types are same, `false` if not */ export const isSameType = (...args: unknown[]): boolean => { for (let i = 1; i < args.length; i++) { if (typeof args[i] === typeof args[i - 1]) continue; return false; } return true; } /** * @description Fucntion generator for custom conditional *type guarding* * @param callback Condition callback function * @returns `Arrow function`, which returns `checkingVariable` is `T` *(boolean)* */ export function generateConditionalGuard<T>(callback: (entity: T) => boolean): (checkingVariable: unknown) => checkingVariable is T { return (checkingVariable: unknown): checkingVariable is T => { return callback(checkingVariable as T); } } /** * * @description Function generator for *type guarding* * @param prop Property to check *(must be string or symbol)* * @param propPrimitive This property `type` alias primitive in string * @returns `Arrow function`, which returns `checkingVariable` is `T` *(boolean)* */ export function generateGuard<T>(prop: keyof T, propPrimitive: string | symbol): (checkingVariable: unknown) => checkingVariable is T { return (checkingVariable: unknown): checkingVariable is T => { return Boolean(checkingVariable) && typeof (checkingVariable as Required<T>)[prop as keyof T] === propPrimitive; } } export type Asserter<T> = (checkingVariable: unknown) => asserts checkingVariable is T /** * @param errorMessage Error message `string` * @param isValid Callback function, that have to return true ro * * @returns Type asserter which asserts `checkingVariable` is `T` *(boolean)* */ export function generateAsserter <T>( errorMessage: string, isValid: (source: unknown, ...args: unknown[]) => boolean, ): (checkingVariable: unknown) => asserts checkingVariable is T { return (source: unknown, ...args: unknown[]): asserts source is T => { const state = isValid(source, ...args) if (!state) throw new Error(errorMessage) } } export interface Predicates<T> { guard: ReturnType<typeof generateGuard<T>>, assert: ReturnType<typeof generateAsserter<T>> } /** * @description Generates predicates by provided validation callback * @param errorMessage Error message `string` for *asserter* * @param validation Validation `callback`, like in *conditional type guard* * @returns Object with both asserter and type guard */ export function generatePredicates<T>( errorMessage: string, validation: (source: unknown, ...args: unknown[]) => boolean ): Predicates<T> /** * @description Generates predicates by provided property and its primitive * @param errorMessage Error message `string` for *asserter* * @param prop Property to check *(must be string or symbol)* * @param propPrimitive This property `type` alias primitive in string * @returns Object with both asserter and type guard */ export function generatePredicates<T>( errorMessage: string, prop: keyof T, propPrimitive: string | symbol ): Predicates<T> export function generatePredicates<T>( errorMessage: string, validationOrProp: keyof T | ((source: unknown, ...args: unknown[]) => boolean), propPrimitive?: string | symbol ): any { if (validationOrProp instanceof Function) { return { guard: generateConditionalGuard<T>(validationOrProp), assert: generateAsserter<T>(errorMessage, validationOrProp as (source: unknown, ...args: unknown[]) => source is T | boolean) } } else if (propPrimitive) { const guard = generateGuard<T>(validationOrProp, propPrimitive) return { guard, assert: generateAsserter<T>( errorMessage, guard ) } } }