My goal is to pass different callback functions as arguments and have them called with the proper parameters.
Here is a simplified example of how it should work. However, determining if process instanceof ITwo
makes no sense and I haven't found an expression that accomplishes this.
interface IOne { (j: string): number; }
interface ITwo { (j: number): number; }
function dualArg(i: string, process: IOne | ITwo): number {
// something along these lines
if (process instanceof ITwo) {
// call with a numeric argument
return process(i);
} else {
// convert to a number
return process(+i);
}
}
function inc(i: number): number {
return ++i;
}
function idem(text: string): number {
return +text;
}
it('determine function signature', () => {
expect(dualArg('1', inc)).toBe(2);
expect(dualArg('1', idem)).toBe(1);
})
For a normal argument, using instanceof
will suffice for TypeScript to recognize it as an object of a specific type. Unfortunately, there isn't a similar solution for functions.
If I resort to hard-coded conditionals like
process.prototype.constructor.name === 'idem'
, TypeScript throws an error message: Cannot invoke an expression whose type lacks a call signature. Type 'IOne | ITwo' has no compatible call signatures.
In such cases, I could define process: any
to bypass TypeScript checks and make the code compile and run. However, my intention is to be able to distinguish functions solely based on their signature, without relying on names or additional flags.