Reputation: 557
I wonder why when I use decorators or annotations in Typescript on a class. The compiler can't infer the new type of the class. If I don't use decorators and use the old way to do this in ES5 (ie. call manually the decorator) it obviously works.
For instance, here a sample that shows the issue:
function decorate(Target: typeof Base): IExtendedBaseConstructor {
return class extends Target implements IExtendedBase {
public extendedtMethod(): number {
return 3;
}
};
}
interface IBase {
baseMethod(): number;
}
interface IExtendedBase extends Base {
extendedtMethod(): number;
}
interface IExtendedBaseConstructor {
new(): IExtendedBase;
}
@decorate
class Base implements IBase {
public baseMethod(): number {
return 5;
}
}
const test = new Base();
test.baseMethod(); // OK
test.extendedtMethod(); // NOT OK, typescript think, Base is still Base but we decorated it.
With the older way, it works:
class Base implements IBase {
public baseMethod(): number {
return 5;
}
}
const ExtendedBase = decorate(Base);
const test = new ExtendedBase();
test.baseMethod(); // OK
test.extendedtMethod(); // OK
Thanks in advance.
Upvotes: 6
Views: 2109
Reputation: 3218
There is a way to make this work with just a little extra coding required.
For any class decorator, create an interface with its properties and methods. Name it in a way so you can easily associate it with the decorator it's describing. In your case, it could be:
interface IDecorate {
extendedMethod(): number;
}
For any class that needs this decorator, you simply create an interface with the same name as the class and let it extend all necessary decorator interfaces:
@decorate
@anotherDecorator
class MyClass {
// ...
}
interface MyClass extends IDecorate, IAnotherDecorator {}
Now, just turn off ESLint's or TSLint's warnings for empty interfaces and you should be ready to go. Any method or property added by the decorator will now be available to use within the decorated class itself.
Upvotes: 0
Reputation: 106620
Right now this doesn't work. There is a pending issue on github to allow class decorators to change the type of the class.
I would recommend doing the "old way" you mentioned until this is implemented.
Upvotes: 4