// This entire implementation courtesy of Anders Hjelsberg: // https://github.com/microsoft/TypeScript/pull/50831#issuecomment-1253830522 import { ReverseHead, ReverseTail } from '../types' type UnknownFunction = (...args: any[]) => any type LongestTuple = T extends [infer U extends unknown[]] ? U : T extends [infer U, ...infer R extends unknown[][]] ? MostProperties> : never type MostProperties = keyof U extends keyof T ? T : U type ElementAt = N extends keyof T ? T[N] : unknown type ElementsAt = { [K in keyof T]: ElementAt } type Intersect = T extends [] ? unknown : T extends [infer H, ...infer T] ? H & Intersect : T[number] type MergeTuples> = { [K in keyof L]: Intersect< ElementsAt extends readonly unknown[] ? ElementsAt : never > } type ExtractParameters = { [K in keyof T]: Parameters } export type MergeParameters = '0' extends keyof T ? MergeTuples>> : Parameters type HasRest = number extends S['length'] ? true : false type HasExplicit = '0' extends keyof S ? true : false type HasCombined = true extends HasExplicit & HasRest ? true : false type MakeRestExplicit = true extends HasCombined ? [ ...ReverseTail, ReverseHead extends readonly unknown[] ? ReverseHead[number] : never ] : true extends HasRest ? [...T] : T