您可以使用 TypeScript 装饰器将属性添加到方法调用吗?
Can you use TypeScript decorators to add properties to a method call?
现在在使用装饰器时 javascript 似乎可以工作(强制编译和方法可用),但是类型太严格了。
如您所见here以下内容无法编译:
declare var _: any;
export function Throttle(milli: number) {
interface Throttled extends Function {
now: Function
}
return function<T extends Throttled>(target: Object, propertyKey: string, descriptor: TypedPropertyDescriptor<Function>): TypedPropertyDescriptor<T> {
let originalMethod = descriptor.value;
// NOTE: Do not use arrow syntax here. Use a function expression in
// order to use the correct value of `this` in this method
descriptor.value = <any>_.throttle(function() {
originalMethod.apply(this, arguments);
}, milli);
(<Throttled>descriptor.value).now = <any>function() {
originalMethod.apply(this, arguments);
};
return <TypedPropertyDescriptor<T>>descriptor;
}
}
class Ctrl {
constructor(scope: any) {
scope.$watch("foo", this.throttledByClassWatch);
this.throttledByClassWatch.now() //unrecommended now call
}
@Throttle(100000)
private throttledByClassWatch() {
}
}
我的类型可能有点不对,但我已经尝试了许多其他排列。好像是因为期望的类型是
declare type MethodDecorator = <T>(target: Object, propertyKey: string | symbol, descriptor: TypedPropertyDescriptor<T>) => TypedPropertyDescriptor<T> | void;
因此输入 T 必须与输出 T 匹配。
理想情况下,now
也可以继承通用类型 T
,因此可以对其进行类型检查。
TypeScript 的类型系统无法描述方法的属性。
你可以做的是这些方面的事情:
interface Throttled extends Function {
now: Function;
}
function Throttle(milli: number) {
return function(target: Object, propertyKey: string, descriptor: TypedPropertyDescriptor<any>) {
let originalMethod = descriptor.value;
descriptor.value = _.throttle(function() {
originalMethod.apply(this, arguments);
}, milli);
(<Throttled>descriptor.value).now = function() {
originalMethod.apply(this, arguments);
};
return descriptor;
};
}
class Ctrl {
constructor(scope: any) {
this.runNow(this.throttledByClassWatch);
}
@Throttle(100000)
private throttledByClassWatch() {
}
private runNow(method: Function, ...args: any[]) {
(method as Throttled).now.apply(this, args);
}
}
基本上,有一个可重用的函数,可以抽象出对受限方法的调用 .now()
。
现在在使用装饰器时 javascript 似乎可以工作(强制编译和方法可用),但是类型太严格了。
如您所见here以下内容无法编译:
declare var _: any;
export function Throttle(milli: number) {
interface Throttled extends Function {
now: Function
}
return function<T extends Throttled>(target: Object, propertyKey: string, descriptor: TypedPropertyDescriptor<Function>): TypedPropertyDescriptor<T> {
let originalMethod = descriptor.value;
// NOTE: Do not use arrow syntax here. Use a function expression in
// order to use the correct value of `this` in this method
descriptor.value = <any>_.throttle(function() {
originalMethod.apply(this, arguments);
}, milli);
(<Throttled>descriptor.value).now = <any>function() {
originalMethod.apply(this, arguments);
};
return <TypedPropertyDescriptor<T>>descriptor;
}
}
class Ctrl {
constructor(scope: any) {
scope.$watch("foo", this.throttledByClassWatch);
this.throttledByClassWatch.now() //unrecommended now call
}
@Throttle(100000)
private throttledByClassWatch() {
}
}
我的类型可能有点不对,但我已经尝试了许多其他排列。好像是因为期望的类型是
declare type MethodDecorator = <T>(target: Object, propertyKey: string | symbol, descriptor: TypedPropertyDescriptor<T>) => TypedPropertyDescriptor<T> | void;
因此输入 T 必须与输出 T 匹配。
理想情况下,now
也可以继承通用类型 T
,因此可以对其进行类型检查。
TypeScript 的类型系统无法描述方法的属性。
你可以做的是这些方面的事情:
interface Throttled extends Function {
now: Function;
}
function Throttle(milli: number) {
return function(target: Object, propertyKey: string, descriptor: TypedPropertyDescriptor<any>) {
let originalMethod = descriptor.value;
descriptor.value = _.throttle(function() {
originalMethod.apply(this, arguments);
}, milli);
(<Throttled>descriptor.value).now = function() {
originalMethod.apply(this, arguments);
};
return descriptor;
};
}
class Ctrl {
constructor(scope: any) {
this.runNow(this.throttledByClassWatch);
}
@Throttle(100000)
private throttledByClassWatch() {
}
private runNow(method: Function, ...args: any[]) {
(method as Throttled).now.apply(this, args);
}
}
基本上,有一个可重用的函数,可以抽象出对受限方法的调用 .now()
。