You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
I really love the power of using const assertions for creating deeply immutable and narrowly typed constants, although I feel they have a relatively major flaw in the fragility they introduce when you have a specific shape of data you want a variable to adhere to, as you ultimately have to go and perform the type-checking manually if you make any human mistakes.
This proposal is to allow us to get the best of both worlds, by introducing a new additional syntax to optionally allow for adding a type annotation to a const assertion, in the same manner you would add a type annotation at the start of a variable normally using a colon. e.g.
The type checking would then effectively perform be performed on the value as it normally would to ensure that the value adheres to the type in the type annotation, and return any errors to be resolved if not.
Importantly however, the actual type of the variable would still remain the deep readonly/immutable type that is generated from using a const assertion.
📃 Motivating Example
Take the following example that the suggestion above references from, where we are trying to get the ANIMALS constant to follow the shape of Record<Animal, AnimalInfo>
enumAnimal{CAT='cat',DOG='dog',MOUSE='mouse';}interfaceAnimalInfo{sound: string;lifeExpectancy: number;}constANIMALS={[Animal.CAT]: {sound: 'meow',lifeExpectancy: 15,},[Animal.DOG]: {sound: 'woof',lifeExpectancy: '10',// NOTE: the type here has accidentally been declared as a string instead of a numberfavoriteFood: 'bone'// NOTE: The AnimalInfo interface does not include a favoriteFood property},// Note: the constant is missing an entry for Animal.MOUSE}asconst;
As you can notice from the embelished example above, it can be quite easy to make mistakes when using const assertions that would ordinarily get picked up as errors just by using a normal type annotation (e.g. const ANIMALS: Record<Animal, AnimaInfo>).
Even if you were to try and use both a normal type annotation and a const assertion like this for example:
unfortunately (though I think it makes some amount of sense), only the type from the type annotation (Record<Animal, AnimalInfo>) is what will get cast for the type of the ANIMALS constant, effectively making the const assertion redundant.
By allowing the type annotation to happen after the const assertion, we can get the desired benefits without introducing any breaking changes.
💻 Use Cases
The general use cases for this have been for the most part covered by the motivating example above. Essentially you would want to use this anywhere where you want to have the benefit of both performing normal type checking for a variable's value against a type annotation to ensure a consistent shape for the value's data, while still having the type of that variable be cast to the narrower, deeply read-only type that is generated from a const assertion.
There aren't really any existing workarounds for this that I am aware of. The best alternative I've been doing personally is just manually adding the type annotation to a variable and removing it again whenever I want to make changes to it while ensuring I'm not breaking the shape of the data.
Any thoughts, feedbacks, suggestions, or criticisms on this propsal would be greatly appreciated🙏
The text was updated successfully, but these errors were encountered:
Suggestion
🔍 Search Terms
const assertions with type annotations, const assertions, type annotations, typed variables with also using as const
✅ Viability Checklist
My suggestion meets these guidelines:
⭐ Suggestion
I really love the power of using const assertions for creating deeply immutable and narrowly typed constants, although I feel they have a relatively major flaw in the fragility they introduce when you have a specific shape of data you want a variable to adhere to, as you ultimately have to go and perform the type-checking manually if you make any human mistakes.
This proposal is to allow us to get the best of both worlds, by introducing a new additional syntax to optionally allow for adding a type annotation to a const assertion, in the same manner you would add a type annotation at the start of a variable normally using a colon. e.g.
The type checking would then effectively perform be performed on the value as it normally would to ensure that the value adheres to the type in the type annotation, and return any errors to be resolved if not.
Importantly however, the actual type of the variable would still remain the deep readonly/immutable type that is generated from using a const assertion.
📃 Motivating Example
Take the following example that the suggestion above references from, where we are trying to get the
ANIMALS
constant to follow the shape ofRecord<Animal, AnimalInfo>
As you can notice from the embelished example above, it can be quite easy to make mistakes when using const assertions that would ordinarily get picked up as errors just by using a normal type annotation (e.g.
const ANIMALS: Record<Animal, AnimaInfo>
).Even if you were to try and use both a normal type annotation and a const assertion like this for example:
unfortunately (though I think it makes some amount of sense), only the type from the type annotation (Record<Animal, AnimalInfo>) is what will get cast for the type of the
ANIMALS
constant, effectively making the const assertion redundant.By allowing the type annotation to happen after the const assertion, we can get the desired benefits without introducing any breaking changes.
💻 Use Cases
The general use cases for this have been for the most part covered by the motivating example above. Essentially you would want to use this anywhere where you want to have the benefit of both performing normal type checking for a variable's value against a type annotation to ensure a consistent shape for the value's data, while still having the type of that variable be cast to the narrower, deeply read-only type that is generated from a const assertion.
There aren't really any existing workarounds for this that I am aware of. The best alternative I've been doing personally is just manually adding the type annotation to a variable and removing it again whenever I want to make changes to it while ensuring I'm not breaking the shape of the data.
Any thoughts, feedbacks, suggestions, or criticisms on this propsal would be greatly appreciated🙏
The text was updated successfully, but these errors were encountered: