import { IfNoDeepValue } from './helpers.js'; import { IfNever, IfTuple } from './type-check.js'; /** * Make all properties in T nullish */ export type NullishObject = { [K in keyof T as IfNever, never, K>]?: T[K] | null; }; /** * Make all properties in T nullish deeply */ export type DeepNullish = { [K in keyof T as IfNever, never, K>]?: IfNoDeepValue< // Do not deep process No-Deep values Exclude > extends true ? T[K] | null : // Deep process objects DeepNullish> | null; }; /** * Make all properties in T nullish deeply including arrays */ export type DeeperNullish = { [K in keyof T as IfNever, never, K>]?: IfTuple< NonNullable > extends true // Deep process tuples positionally ? DeeperNullishTuple> | null : NonNullable< // Deep process arrays T[K] > extends readonly (infer U)[] ? NonNullable extends any[] ? DeeperNullish[] | null // was mutable - DeeperNullish doesn't touch mutability : readonly DeeperNullish[] | null // was readonly - preserve that : // Do not deep process No-Deep values IfNoDeepValue> extends true ? T[K] | null : // Deep process objects DeeperNullish> | null; }; type DeeperNullishTuple = T extends readonly [infer Head, ...infer Rest] ? [ IfNoDeepValue> extends true ? Head : DeeperNullish>, ...DeeperNullishTuple, ] : [];