TypeScript recognises static class methods as valid properties that adhere to an interface when passing the class object as an argument, however it does not like them when the same interface is used to implement the class.
E.g. In the example below, TypeScript accepts that the Dog class adheres to the AnimalMethods interface when it is passed as an argument inside the callAnimalMethods function, however upon attempting to constrain the Dog class structure by using implements AnimalMethods, the following error is given:
Class 'Dog' incorrectly implements interface 'AnimalMethods'.
Property 'walk' is missing in type 'Dog' but required in type 'AnimalMethods'
Example:
// error here
class Dog implements AnimalMethods {
public static walk(): string {
return 'walk';
}
}
interface AnimalMethods {
readonly walk: () => string,
}
function callAnimalMethods(animalObj: AnimalMethods): void {
animalObj.walk();
}
callAnimalMethods(Dog);
Could someone explain why TypeScript does not allow static methods like this to adhere to an interface, especially when the structure is recognised when using the class in an argument.
Playground link.
class Foo implements Bar {}it means an instance ofFoocan be used as aBar. In your example,new Dog().walk()doesn't work, soDogdoes not implementAnimalMethods. TS doesn't have a way to annotate that a class's static side implements an interface; see github.com/microsoft/TypeScript/issues/33892 for a feature request to do so. If it did, then you could maybe sayclass Dog implements static AnimalMethodsor something. But it doesn't so we can't. Does this address your question fully (and I can write an answer) or am I missing something?const Dog: AnimalMethods = class Dog { public static walk() ... }which worksstaticmethods and not instance methods which are common for classes though. A really nice workaround nevertheless!