[英]Class decorator with stage-2 proposal and Babel 7
我正在玩第 2 階段裝飾器提案,我發現類裝飾器存在一些問題。 在遺留裝飾器中,下一個示例有效,因為類裝飾器將目標構造函數作為其唯一參數,但在第 2 階段提議中接收對象描述符。
function log(Class) {
return (...args) => {
console.log(`Arguments: ${args}`);
return new Class(...args);
};
}
@log
class Bar {
constructor(name, age) { }
}
我已經閱讀了 tc39 提案裝飾器和內置裝飾器,但它對我沒有多大幫助。 我怎樣才能讓這個例子與新的提案裝飾器一起工作? 是否可以在 babel 中使用內置裝飾器?
為了嘗試一些東西,我開發了自己的基本包裝裝飾器,它按預期方法工作,並且我想將其功能擴展到類。
const wrap = f => {
return wrapped => {
const { kind } = wrapped;
if (kind === 'class') {
return f(wrapped);
}
const { descriptor } = wrapped;
const original = descriptor.value;
descriptor.value = f(original);
return { ...wrapped, descriptor };
};
};
export default wrap;
使用這個基本的裝飾器,我可以創建例如這個有效的記錄器方法裝飾器。
import wrap from './wrap';
const loggerFunction = f => {
const name = f.name;
return function test(...args) {
console.log(`starting ${name} with arguments ${args.join(', ')}`);
return f.call(this, ...args);
};
};
export default wrap(loggerFunction);
我可以通過這種方式使用它:
class Foo {
@logger
method(argument) {
return argument;
}
}
你的問題有點老了,但我認為它仍然是實際的,所以這是我的答案:
TLDR:使用一個finisher
財產使用非傳統的階段2個裝飾時,包裹類。
第 2 階段的 API 沒有完全記錄,並且缺少一些東西和用例。
為了實現您想要的效果,請在裝飾器中返回的對象上定義一個特殊的finisher
屬性。
因此,這個legacy
stage-1 裝飾器代碼:
function log(Class) {
return (...args) => {
console.log(`Arguments: ${args}`);
return new Class(...args);
};
}
@log
class Bar {
constructor(name, age) { }
}
將等效於這個non-legacy
第 2 階段裝飾器代碼:
function log(descriptor) {
return {
...descriptor,
finisher: (Class) => (...args) => {
console.log(`Arguments: ${args}`);
return new Class(...args);
},
};
}
@log
class Bar {
constructor(name, age) {}
}
您可以將相同的原則應用於wrap
功能。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.