I have defined the following interface in typescript:
interface MyInterface { () : string; }
This interface simply introduces a call signature that takes no parameters and returns a string. How do I implement this type in a class? I have tried the following:
class MyType implements MyInterface { function () : string { return "Hello World."; } }
The compiler keeps telling me that
Class 'MyType' declares interface 'MyInterface' but does not implement it: Type 'MyInterface' requires a call signature, but Type 'MyType' lacks one
How can I implement the call signature?
In TypeScript we can express its type as: ( a : number , b : number ) => number. This is TypeScript's syntax for a function's type, or call signature (also called a type signature). You'll notice it looks remarkably similar to an arrow function—this is intentional!
Create an instance of Foo to be able to call it: let foo:Foo = new Foo(); let result:number = foo. calcSomeThing( parameter ); Never use var in Typescript - let is your friend.
You can do this by using the new keyword, followed by a syntax similar to that of an arrow function, where the parameter list contains the parameters expected by the constructor and the return type is the class instance this constructor returns. The TypeScript compiler now will correctly compile your code.
Classes can't match that interface. The closest you can get, I think is this class, which will generate code that functionally matches the interface (but not according to the compiler).
class MyType implements MyInterface { constructor { return "Hello"; } } alert(MyType());
This will generate working code, but the compiler will complain that MyType
is not callable because it has the signature new() = 'string'
(even though if you call it with new
, it will return an object).
To create something that actally matches the interface without the compiler complaining, you'll have to do something like this:
var MyType = (() : MyInterface => { return function() { return "Hello"; } })(); alert(MyType());
In case if callable interface should have other methods you can do it like this:
interface Greeter { (): void; setName(name: string): void; } class ConsoleGreeter { private constructor( // constructable via `create()` private name = 'world' ) {} public call(): void { console.log(`Hello ${this.name}!`); } public setName(name: string) { this.name = name; } public static create(): Greeter { const instance = new ConsoleGreeter(); return Object.assign( () => instance.call(), { setName: (name: string) => instance.setName(name) // ... forward other methods } ); } } const greeter = ConsoleGreeter.create(); greeter(); // prints 'Hello world!' greeter.setName('Dolly'); greeter(); // prints 'Hello Dolly!'
Downside: greeter instanceof ConsoleGreeter
is false
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With