import { DropKeys } from '@typed/common' import { Defined, Primitive } from '@typed/lambda' export type Prop = K extends keyof T ? T[K] : undefined export type ObjectPath = Keys extends [] ? T : Keys extends [keyof T] ? Prop : Keys extends [PropertyKey, PropertyKey] ? Prop, Keys[1]> : Keys extends [PropertyKey, PropertyKey, PropertyKey] ? Prop, Keys[1]>, Keys[2]> : Keys extends [PropertyKey, PropertyKey, PropertyKey, PropertyKey] ? Prop, Keys[1]>, Keys[2]>, Keys[3]> : Keys extends [PropertyKey, PropertyKey, PropertyKey, PropertyKey, PropertyKey] ? Prop, Keys[1]>, Keys[2]>, Keys[3]>, Keys[4]> : undefined export type ValuesOf = { [K in keyof A]: A[K] }[keyof A] export type OptionalPropertyNames = { [K in keyof A]-?: undefined extends A[K] ? K : never }[keyof A] export type RequiredPropertyNames = { [K in keyof A]-?: undefined extends A[K] ? never : K }[keyof A] export type OptionalProperties = Pick> export type RequiredProperties = Pick> export type MergeObjects = { [K in Exclude, OptionalPropertyNames>]: K extends keyof B ? K extends keyof A ? Defined : B[K] : K extends keyof A ? A[K] : never } & { [K in Exclude, RequiredPropertyNames>]?: K extends keyof B ? K extends keyof A ? Defined : B[K] : K extends keyof A ? A[K] : never } export type Overwrite = B & MergeObjects, B> export type OptionalKeys = DropKeys & Partial> export type Immutable = A extends Primitive ? A : A extends (infer B)[] ? ImmutableArray : A extends Map ? ImmutableMap : A extends Set ? ImmutableSet : ImmutableObject export interface ImmutableArray extends ReadonlyArray> {} export interface ImmutableMap extends ReadonlyMap, Immutable> {} export interface ImmutableSet extends ReadonlySet> {} export type ImmutableObject = { +readonly [K in keyof A]: Immutable } export type ExtractUnionMember< A extends object, Tag extends keyof A, Value extends A[Tag] > = Extract> export type Mutable = A extends Primitive ? A : A extends ImmutableArray ? MutableArray : A extends ReadonlyArray ? MutableArray : A extends ImmutableMap ? MutableMap : A extends ReadonlyMap ? MutableMap : A extends ImmutableSet ? MutableSet : A extends ReadonlySet ? MutableSet : MutableObject export interface MutableMap extends Map, Mutable> {} export interface MutableSet extends Set> {} export interface MutableArray extends Array> {} export type MutableObject = { -readonly [K in keyof A]: Mutable }