ARTICLE AD BOX
In the answers to the question this duplicates the limitation mentioned in @ford04's answer here, that infer only looks at the last overloaded signature, is acknowledged. This is a missing feature or design limitation of TypeScript; see microsoft/TypeScript#29732 for a relevant feature request.
But this answer shows it's not completely impossible; you can tease out some information about overloads, at least for functions with up to some arbitrary fixed number of them (this is still true as of TypeScript 4.8; recursive conditional types don't help). But it's hairy and ugly and there might be bugs in it, see microsoft/TypeScript#28867. Here's one way of doing it:
type Overloads<T> = T extends { (...args: infer A1): infer R1; (...args: infer A2): infer R2; (...args: infer A3): infer R3; (...args: infer A4): infer R4 } ? [ (...args: A1) => R1, (...args: A2) => R2, (...args: A3) => R3, (...args: A4) => R4 ] : T extends { (...args: infer A1): infer R1; (...args: infer A2): infer R2; (...args: infer A3): infer R3 } ? [ (...args: A1) => R1, (...args: A2) => R2, (...args: A3) => R3 ] : T extends { (...args: infer A1): infer R1; (...args: infer A2): infer R2 } ? [ (...args: A1) => R1, (...args: A2) => R2 ] : T extends { (...args: infer A1): infer R1 } ? [ (...args: A1) => R1 ] : any type OverloadedParameters<T> = Overloads<T> extends infer O ? { [K in keyof O]: Parameters<Extract<O[K], (...args: any) => any>> } : never type OverloadedReturnType<T> = Overloads<T> extends infer O ? { [K in keyof O]: ReturnType<Extract<O[K], (...args: any) => any>> } : neverThe Overloads<T> type alias takes a function type T and returns a tuple of its call signatures (for up to four overloads). And OverloadedParameters<T> and OverloadedReturnType<T> map Parameters<T> and ReturnType<T> over that tuple, respectively.
Let's see it in action (after correcting your example so that it actually has multiple overloads, as done in the other answer):
function example(a: string): number function example(a: string, b: string): number function example(a: string, b?: string): number { return 1 } type ExampleOverloads = Overloads<typeof example> // type ExampleOverloads = [(a: string) => number, (a: string, b: string) => number] type ExampleParameters = OverloadedParameters<typeof example> // type ExampleParameters = [[string], [string, string]]Looks reasonable to me. Okay, hope that helps; good luck!
