I am currently facing a challenge in defining a function that can wrap any other function while maintaining the parameter types and return type. I have managed to achieve this when the function does not use generics, but I am encountering difficulties with generic functions. Here is a simplified example:
function wrap<F extends (...args: any[]) => any>(test: F) {
return (...args: Parameters<typeof test>): ReturnType<typeof test> => {
return test(...args);
};
}
function simpleTest(a: number): number {
return a;
}
// functioning correctly
// type: (a: number) => number
const wrappedSimpleTest = wrap(simpleTest);
function genericTest<T>(a: T): T {
return a;
}
// experiencing issues here
// type: (a: unknown) => unknown
// desired type: <T>(a: T) => T
const wrappedGenericTest = wrap(genericTest);
function genericTest2<T, U>(a: T, b: U): T|U {
return Math.random() < 0.5 ? a : b;
}
// encountering problems here as well
// type: (a: unknown, b: unknown) => unknown
// desired type: <T, U>(a: T, b: U) => T|U
const wrappedGenericTest2 = wrap(genericTest2);