microsoft / microsoft/TypeScript

[decorator metadata] implicit runtime reference created

Ouverte
#42,679 4 commentaires 2 réactions 1 personne assignée Voir sur GitHub

@rbuckton y travaille déjà.

Depuis le 12/2/2021.

Bug Domain: Decorators Rescheduled
Langage dominant
Go
Étoiles
111k
Forks
14.3k
Merge moyen
2 j 4 h
PR mergées (30 j)
132

Description

Bug Report

🔎 Search Terms

decorator metadata shadow same name generic
(also searched in the "Domain: Decorators" tag)

🕗 Version & Regression Information
  • This is the behavior in every version I tried, and I reviewed the FAQ for entries about decorators
⏯ Playground Link

Playground link with relevant code

💻 Code
import { Test } from './Test';

declare function deco(..._param: any): any;

export class Clazz {
  @deco
  method<Test>(Test: Test) {

  }
}
🙁 Actual behavior

As far as TS's unused vars logic is concerned - the above code just creates a type reference on the generic Test:
image

However when you look at the generated code:

__decorate([
    deco,
    __metadata("design:type", Function),
    __metadata("design:paramtypes", [typeof (_a = typeof Test !== "undefined" && Test) === "function" ? _a : Object]),
    __metadata("design:returntype", void 0)
], Clazz.prototype, "method", null);

The decorator actually creates an implicit value reference on the import Test.

Which means if you want to satisfy the noUnusedLocals error, you will (unknowingly) change the runtime behaviour.

🙂 Expected behavior

I think this is the intended behaviour? TBH I'm not entirely sure.
I haven't found any docs about how it's supposed to work.
I think it should not be generating any runtime references.

__decorate([
    deco,
    __metadata("design:type", Function),
    __metadata("design:paramtypes", [Object]),
    __metadata("design:returntype", void 0)
], Clazz.prototype, "method", null);

For context, in @typescript-eslint we have a scope analyser which also attempts to understand the runtime value references created by emitDecoratorMetadata. This understanding means lint rules like no-unused-vars and consistent-type-imports can understand the runtime code and provide correct lints/fixes. This logic was particularly added for consistent-type-imports, which broke people's code due to it not understanding that decorators created implicit value references.

A user presented a bug due to an (incorrect reference) - https://github.com/typescript-eslint/typescript-eslint/issues/2994.
Whilst investigating the fix, I want to ensure it's fixed correctly for all cases, including the one presented above.

If it's entirely intentional that this creates a value reference - then I'll make the referencer work the same way.

Guide de contribution

Ouvrir le guide de contribution

Par où commencer

  1. Lisez l'issue en entier, puis le guide de contribution du projet.
  2. Signalez en commentaire que vous la prenez — cela évite que deux personnes fassent le même travail.
  3. Forkez le dépôt et travaillez sur une branche.
  4. Ouvrez une pull request qui référence le numéro de l'issue.

Évaluation

Cette issue n'a pas encore été évaluée.

Recevez les nouvelles issues par e-mail

Un résumé court des issues GitHub adaptées aux débutants.