Typescript: Wrong overload selection based on function return type

Multi tool use
Multi tool use


Typescript: Wrong overload selection based on function return type



Why the following code is a compile error:


export interface Timer { }
declare function setInterval(callback: (...args: any) => void, ms: number, ...args: any): Timer;
declare function setInterval(handler: (...args: any) => void, timeout: number): number;

const timer: number = setInterval(() => console.log('hi'), 1000);



Also, when I change the order of declare function statements, it compiles the code without any errors. Looks like compiler just accepts the first type declaration.


declare function



EDIT: I couldn't provide a link to playground because the url was not correctly formatted in the question and I couldn't use any url shortener!




1 Answer
1



The problem is that Typescript does not (usually) take into account the expected call site return type when resolving function signatures. In your case just looking at setInterval(() => console.log('hi'), 1000); the compiler can say that this call could resolve to either signature, so it picks the first one in declaration order (as specified in the compiler specs). Once it has picked an overload the compiler will not reverse the decision if later, on assignment an error occurs.


setInterval(() => console.log('hi'), 1000);



The real problem to me seems to be that in deed, even I, lookin at setInterval(() => console.log('hi'), 1000); can't tell if it will return a number or a Timer. There is nothing distinguishing between a call with two arguments returning a number, and a call to the version with two arguments and an empty rest parameter returning a Timer


setInterval(() => console.log('hi'), 1000);


number


Timer


Timer





Thanks for your answer. The first setInterval definition pasted from node's type definitions in definitely typed. I don't think writing window.setInterval is a clean way of fixing this problem. What would be the best fix for this? Changing type definition of node in definitely typed?
– alisabzevari
Jul 1 at 21:17


setInterval


window.setInterval





@alisabzevari My recommendation then is to remove the dom lib from the default libs. For example: "lib": ["es2018", "scripthost"]. This will remove setInterval from the global namespace and leave just the ndoe version around.
– Titian Cernicova-Dragomir
Jul 2 at 7:14


dom


"lib": ["es2018", "scripthost"]


setInterval





I actually want to use setInterval from dom. I have to remove node from type definitions, but this has been added from one of my node_modules packages.
– alisabzevari
2 days ago


setInterval


dom


node






By clicking "Post Your Answer", you acknowledge that you have read our updated terms of service, privacy policy and cookie policy, and that your continued use of the website is subject to these policies.

mY0P,8C7mo,Fw,3K7NgDobM3Irfb zlx8VKPNv9kyagkegeeiJllWnhxAv,Xau
EJxh0pET p1aQPalByFDdQMdbpmrIuOaz4RveRtFbiKbCCXd,cKgIQ1oz,DzYu2,yE4uaDi

Popular posts from this blog

PySpark - SparkContext: Error initializing SparkContext File does not exist

django NoReverseMatch Exception

List of Kim Possible characters