Skip to content

Commit af8a5a5

Browse files
Add support for up to five function overloads (#95)
* add support for upto five function overloads * add overloading support for terminating functions * fix typo on function name
1 parent 61ed7a0 commit af8a5a5

File tree

1 file changed

+47
-5
lines changed

1 file changed

+47
-5
lines changed

src/Transformations.ts

Lines changed: 47 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -1,11 +1,49 @@
11
import { AllArguments } from "./Arguments";
22

3-
export type NoArgumentFunctionSubstitute<TReturnType> = (() => (TReturnType & NoArgumentMockObjectMixin<TReturnType>))
3+
type FunctionSubstituteWithOverloads<TFunc, Terminating = false> =
4+
TFunc extends {
5+
(...args: infer A1): infer R1;
6+
(...args: infer A2): infer R2;
7+
(...args: infer A3): infer R3;
8+
(...args: infer A4): infer R4;
9+
(...args: infer A5): infer R5;
10+
} ?
11+
FunctionHandler<A1, R1, Terminating> & FunctionHandler<A2, R2, Terminating> &
12+
FunctionHandler<A3, R3, Terminating> & FunctionHandler<A4, R4, Terminating>
13+
& FunctionHandler<A5, R5, Terminating> : TFunc extends {
14+
(...args: infer A1): infer R1;
15+
(...args: infer A2): infer R2;
16+
(...args: infer A3): infer R3;
17+
(...args: infer A4): infer R4;
18+
} ?
19+
FunctionHandler<A1, R1, Terminating> & FunctionHandler<A2, R2, Terminating> &
20+
FunctionHandler<A3, R3, Terminating> & FunctionHandler<A4, R4, Terminating> : TFunc extends {
21+
(...args: infer A1): infer R1;
22+
(...args: infer A2): infer R2;
23+
(...args: infer A3): infer R3;
24+
} ?
25+
FunctionHandler<A1, R1, Terminating> & FunctionHandler<A2, R2, Terminating>
26+
& FunctionHandler<A3, R3, Terminating> : TFunc extends {
27+
(...args: infer A1): infer R1;
28+
(...args: infer A2): infer R2;
29+
} ?
30+
FunctionHandler<A1, R1, Terminating> & FunctionHandler<A2, R2, Terminating> : TFunc extends {
31+
(...args: infer A1): infer R1;
32+
} ?
33+
FunctionHandler<A1, R1, Terminating> : never;
34+
35+
type Equals<A, B> = (<T>() => T extends A ? 1 : 2) extends (<T>() => T extends B ? 1 : 2) ? true : false;
36+
type FunctionHandler<TArguments extends any[], TReturnType, Terminating> =
37+
Equals<TArguments, unknown[]> extends true ?
38+
{} : Terminating extends true ?
39+
TerminatingFunction<TArguments> :
40+
FunctionSubstitute<TArguments, TReturnType>
441

542
export type FunctionSubstitute<TArguments extends any[], TReturnType> =
643
((...args: TArguments) => (TReturnType & MockObjectMixin<TArguments, TReturnType>)) &
744
((allArguments: AllArguments) => (TReturnType & MockObjectMixin<TArguments, TReturnType>))
845

46+
export type NoArgumentFunctionSubstitute<TReturnType> = (() => (TReturnType & NoArgumentMockObjectMixin<TReturnType>))
947
export type PropertySubstitute<TReturnType> = (TReturnType & Partial<NoArgumentMockObjectMixin<TReturnType>>);
1048

1149
type MockObjectPromise<TReturnType> = TReturnType extends Promise<infer U> ? {
@@ -32,17 +70,21 @@ export type ObjectSubstitute<T extends Object, K extends Object = T> = ObjectSub
3270
mimick(instance: T): void;
3371
}
3472

73+
type TerminatingFunction<TArguments extends any[]> = ((...args: TArguments) => void) & ((arg: AllArguments) => void)
74+
3575
type TerminatingObject<T> = {
3676
[P in keyof T]:
37-
T[P] extends (...args: infer F) => any ? ((...args: F) => void) & ((arg: AllArguments) => void) :
38-
T[P] extends () => any ? () => void :
77+
T[P] extends (...args: infer F) => any ?
78+
F extends [] ? () => void :
79+
FunctionSubstituteWithOverloads<T[P], true> :
3980
T[P];
4081
}
4182

4283
type ObjectSubstituteTransformation<T extends Object> = {
4384
[P in keyof T]:
44-
T[P] extends (...args: infer F) => infer R ? FunctionSubstitute<F, R> :
45-
T[P] extends () => infer R ? NoArgumentFunctionSubstitute<R> :
85+
T[P] extends (...args: infer F) => infer R ?
86+
F extends [] ? NoArgumentFunctionSubstitute<R> :
87+
FunctionSubstituteWithOverloads<T[P]> :
4688
PropertySubstitute<T[P]>;
4789
}
4890

0 commit comments

Comments
 (0)