A problematic situation arises with TypeScript when attempting to type-check a function that returns a specific function based on its arguments. The issue is best illustrated through the following simplified example:
type NoiseMaker<T extends Animal> = (animal: T) => void;
class Dog {
bark() {
console.log('Woof! Woof!');
}
}
class Cat {
meow() {
console.log('Meow')
}
}
type Animal = Dog | Cat;
const bark: NoiseMaker<Dog> = (dog: Dog) => {
dog.bark();
}
function getNoiseMaker<T extends Animal>(animal: T): NoiseMaker<T> {
if (animal instanceof Dog) {
// Since T is a Dog, why does TypeScript raise an error?
return bark;
}
else {
throw new Error("I don't know that kind of animal");
}
}
The question remains: why does TypeScript not allow the return of bark
in this scenario once it recognizes that the type of T
matches or extends Dog?
There seems to be a mistake somewhere - can you spot it?