我可以在对象属性上使用装饰器吗?

Chr*_*ris 7 javascript decorator typescript

通常我会像这样应用装饰器:

class SpecialMethods {
    @Deco
    static someMethod() {
    }
}
Run Code Online (Sandbox Code Playgroud)

是否还有一些方法可以将它与普通对象而不是类一起使用:

const SpecialMethods = {
    @Deco
    someMethod: () => {}
}
Run Code Online (Sandbox Code Playgroud)

Sha*_*ard 5

是的,但是不是很实用。您可以为对象的属性调用装饰器,但不能以与装饰类及其内容相同的方式调用。

给定以下装饰器:

const TestDecorator = (at: string) => {
    return function (target: any, prop: string, descriptor?: PropertyDescriptor) {
        console.log(`decorated at ${at}}`);
    }
}
Run Code Online (Sandbox Code Playgroud)

将在班级中使用:

class TestClass {
    @TestDecorator('class method')
    public testMethod() { }
}
Run Code Online (Sandbox Code Playgroud)

但是,不能对属性使用与上述相同的方法:

const testObj = {
    @TestDecorator('property method')
    testMethod: () => { }
};
Run Code Online (Sandbox Code Playgroud)

要解决此问题,您可以在属性处调用装饰器。

首先,您必须声明对象及其所有属性:

const testObj = {
    testMethod: () => { }
};
Run Code Online (Sandbox Code Playgroud)

我的装饰员期望使用咖喱值:

const deco = TestDecorator('property method');
Run Code Online (Sandbox Code Playgroud)

现在,您必须在中手动调用deco属性的装饰器testObj

deco(testObj, 'testMethod');
Run Code Online (Sandbox Code Playgroud)

如果需要propertyDescriptor在装饰器中使用(不在OP中),则还必须手动提供它:

deco(testObj, 'testMethod', Object.getOwnPropertyDescriptor(testObj, 'testMethod'));
Run Code Online (Sandbox Code Playgroud)

这是TS游乐场。在控制台中检查输出。