microsoft / microsoft/TypeScript
Generic decorators - could they receive some default type arguments?
まだ誰も着手していません。
- 主要言語
- Go
- スター
- 111k
- フォーク
- 14.3k
- 平均マージ
- 2日 4時間
- マージ済み PR(30日)
- 132
説明
A decorator can receive arguments, by being defined as a function that accepts parameters and then returns a normal decorator function:
```
function computed(evaluator: (obj: any) => any) {
return (obj: any, key: string) => {
Object.defineProperty(obj, key, {
get() { return evaluator(obj); }
});
};
}
```
I could use the above example like this:
```
class C {
firstName = "Homer";
lastName = "Simpson";
@computed(c => c.firstName + " " + c.lastName)
fullName: string;
}
```
Not a realistic example in that it's just another way of defining a property getter, but it's enough to demonstrates the general problem: `c` is of type `any` so the access to `firstName` and `lastName` is not type-checked, and nor is the result of the expression.
We can attempt to address this manually, because decorators can be generic:
```
function computed(evaluator: (obj: O) => R) {
return (obj: O, key: string) => {
Object.defineProperty(obj, key, {
get() { return evaluator(obj); }
});
};
}
class C {
firstName = "Homer";
lastName = "Simpson";
@computed(c => c.firstName + " " + c.lastName)
fullName: string;
}
```
But this still doesn't close the loop. The compiler is happy with the following abuse, in which `c` is supposedly a `string` but is actually a `C`, and `fullName` is declared a `string` but will actually become a `number` (albeit `NaN` I guess):
```
@computed(c => parseInt(c, 10))
fullName: string;
```
In summary: decorators are passed the values of the meta-information in standard parameters (`target`, `key`, `value`), but they are not passed the compile-time types of those values in a way that can be used to create fully type-safe decorators.
So it would be helpful if in decorator-defining functions with generic parameters, those parameters could somehow map automatically to the types of `target` and `value` (as given meaning in the `__decorate` helper).
For big yucks, a straw man in which the compiler recognises a couple of built-in decorators that can appear on the type parameters:
```
function computed<@decoratorTarget O, @decoratorValue R>(evaluator: (obj: O) => R) {
...
}
```
Being decorated in this way, it would not be possible to manually specify type arguments for those type parameters when using the decorator. They would effectively be invisible to the user. If the decorator has its own custom type parameters, they would appear from the outside to be the only parameters (and for clarity should be at the front of the list).
コントリビューションガイド
はじめの一歩
- issue を最後まで読み、次にプロジェクトのコントリビューションガイドを読みます。
- 着手することを issue にコメントします — 二人が同じ作業をするのを防げます。
- リポジトリをフォークし、ブランチを切って変更します。
- issue 番号を参照したプルリクエストを送ります。
調査の方向性
この issue にはデコレーターとジェネリック型引数の例が示されていますが、リポジトリ内のファイル、テスト、エントリーポイントは示されていません。まず、デコレーターの型チェックとジェネリック引数の推論を行う compiler の領域を特定し、次に、型安全な target と value の推論を検証するために必要なサポート対象の動作とテストを定義してください。
索引モデルが issue の本文から書いたものです。
評価
- 技術スタック
- typescript
- 領域
- compilers
- issue の種類
- 機能追加
- 難易度
- 5/5
- 見積もり時間
- 1週間以上
- 活発さ
- 停滞
- 明瞭さ
- 説明が足りない
- 初心者へのやさしさ
- 25/100