microsoft / microsoft/TypeScript

Lazily evaluated template literal types

Ouverte
#43,335 12 commentaires 66 réactions 0 personnes assignées Voir sur GitHub

Personne n'a encore pris cette issue.

Awaiting More Feedback Suggestion
Langage dominant
Go
Étoiles
111k
Forks
14.3k
Merge moyen
1 j 19 h
PR mergées (30 j)
117

Description

Suggestion

Template literal types seem to be resolved immediately, which makes the combinatorics blow up and the whole thing much less useful than it would seem to be at first.

For example I can't even represent a type equals to 5 consecutive digits with the current system without getting a "too complex" error:

type Digit = 0 | 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9;
type UUID = `${Digit}${Digit}${Digit}${Digit}${Digit}`;

The current system may be more composable than regexes, but if it's not even able to represent something like /\d{5}/ I'd argue that's not a replacement for it at all.

The suggestion is that there's no need to resolve all the possible combinations at all, but a divide and conquer approach should be implemented where each little piece of the template literal does it's job individually and when all little pieces match than the whole thing matches.

🔍 Search Terms

  • template literal
  • lazy

✅ Viability Checklist

  • This wouldn't be a breaking change in existing TypeScript/JavaScript code
  • This wouldn't change the runtime behavior of existing JavaScript code
  • This could be implemented without emitting different JS based on the types of the expressions
  • This isn't a runtime feature (e.g. library functionality, non-ECMAScript syntax with JavaScript output, new syntax sugar for JS, etc.)
  • This feature would agree with the rest of TypeScript's Design Goals.

⭐ Suggestion

Evaluate template literal types lazily to not make the combinatorics blow up. Meaning that each little piece of the template literal should be its own little function that performs some type matching internally, so there's no need to resolve all the possible combinations at all.

📃 Motivating Example

I can't even represent the equivalent of /\d{5}/ currently.

type Digit = 0 | 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9;
type UUID = `${Digit}${Digit}${Digit}${Digit}${Digit}`;

💻 Use Cases

For example creating a type for UUID strings, which are a fairly common thing.

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.

Piste de recherche

Commencez par l’exemple TypeScript motivant dans l’issue : un type de littéral de gabarit à cinq chiffres construit à partir de l’union Digit. Étudiez l’évaluation et le comportement de correspondance des types de littéraux de gabarit du compilateur ; le travail est terminé lorsque ce type peut être représenté et utilisé sans déclencher l’erreur actuelle "too complex", tout en préservant la correspondance des types de littéraux de gabarit.

Rédigé par le modèle d'indexation à partir du texte de l'issue.

Évaluation

Stack technique
typescript
Domaine
compilers
Type d'issue
Fonctionnalité
Difficulté
5/5
Temps estimé
Plus d'une semaine
Activité
À l'abandon
Clarté
Plutôt claire
Accessibilité débutants
25/100

Recevez les nouvelles issues par e-mail

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