TypeScript-相互依赖修饰符
从打字稿 因此,在评估多个项目时,将执行以下步骤 TypeScript中单个声明上的装饰器:TypeScript-相互依赖修饰符,typescript,Typescript,从打字稿 因此,在评估多个项目时,将执行以下步骤 TypeScript中单个声明上的装饰器: 每个装饰器的表达式从上到下进行计算。 然后将结果作为从底部到顶部的函数调用 问题 我有两个装饰师,其中一个装饰师依赖另一个: 示例 @test() @testCase({...}) public doSomething(): void { } @testCase()依赖于@test(),因为在将测试用例添加到测试之前,需要将测试添加到测试运行程序中 我可以 @testCase({...}) @test
@test()
@testCase({...})
public doSomething(): void {
}
@testCase()
依赖于@test()
,因为在将测试用例添加到测试之前,需要将测试添加到测试运行程序中
我可以
@testCase({...})
@test()
public doSomething(): void {
}
但在声明某个东西是测试之前声明测试用例似乎有些奇怪
有没有办法让装饰器相互依赖,即
testCase
必须在test
之后出现?您可以在testCase
中向目标函数添加额外信息,然后在test
装饰器中检查额外信息。在额外信息的下面是一个回调,更多的装饰者可以对此做出贡献。这提供了很大的灵活性,但是您可以添加其他信息而不是回调,并在测试中使用这些信息
interface IAfterTestRegistered {
afterTestRegisteredCallback?: ()=> void
}
// We could potentially have more then one contributor that need a callback executed.
function addCallback(obj: IAfterTestRegistered, callback : () => void) {
let oldCallback = obj.afterTestRegisteredCallback;
if(oldCallback != undefined) {
obj.afterTestRegisteredCallback = () =>{
oldCallback();
callback();
}
}
else{
obj.afterTestRegisteredCallback = callback;
}
}
function test() : MethodDecorator {
return function<T>(target: Object, propertyKey: string | symbol, descriptor: TypedPropertyDescriptor<T>) : void {
console.log("test");
let targetFunction: IAfterTestRegistered = target[propertyKey];
if(targetFunction.afterTestRegisteredCallback) {
targetFunction.afterTestRegisteredCallback();
}
}
}
function testCase(data: { index: number}) : MethodDecorator {
return function<T>(target: Object, propertyKey: string | symbol, descriptor: TypedPropertyDescriptor<T>) : void {
console.log(`testcase ${data.index}`);
addCallback(target[propertyKey], () =>
{
console.log(`after-register testcase ${data.index}`);
});
}
}
class myClass {
@test()
@testCase({ index: 1 })
@testCase({ index: 2 })
public doSomething(): void {
}
}
// Will output
// testcase 2
// testcase 1
// test
// after-register testcase 2
// after-register testcase 1
接口IAfterTestRegistered{
后注册回调?:()=>无效
}
//我们可能有多个参与者需要执行回调。
函数addCallback(obj:IAfterTestRegistered,callback:()=>void){
设oldCallback=obj.afterestregisteredcallback;
if(oldCallback!=未定义){
obj.afterestRegisteredCallback=()=>{
oldCallback();
回调();
}
}
否则{
obj.afterestRegisteredCallback=回调;
}
}
函数测试():MethodDecorator{
返回函数(目标:对象,属性key:string |符号,描述符:TypedPropertyDescriptor):void{
控制台日志(“测试”);
let targetFunction:IAfterTestRegistered=target[propertyKey];
if(targetFunction.AfterestRegisteredCallback){
targetFunction.afterTestRegisteredCallback();
}
}
}
函数testCase(数据:{index:number}):MethodDecorator{
返回函数(目标:对象,属性key:string |符号,描述符:TypedPropertyDescriptor):void{
log(`testcase${data.index}`);
addCallback(目标[propertyKey],()=>
{
log(`after register testcase${data.index}`);
});
}
}
类myClass{
@测试()
@testCase({index:1})
@testCase({index:2})
公共doSomething():无效{
}
}
//将输出
//测试用例2
//测试用例1
//试验
//在寄存器测试用例2之后
//在寄存器测试用例1之后
这是针对您正在编写的库,还是仅针对您正在使用的库?@Fenton针对我正在编写的库。或者,您可以删除decorator的副作用,只使用有关方法的元数据对类进行注释。然后(在其他地方)在运行时检查类中的所有元数据并相应地进行操作。可以更好地扩展到相互依赖的多个装饰器。@ChrisDevereux,没错,这也是一个不错的选择。您可以随意添加它作为一个答案:)为什么不将两个decorator组合成一个并使用它呢?