If you hit the limits of TS’s inference capabilities it doesn’t necessarily react — as you would hope for — with a graceful degradation (what would be a compiler error “Type instantiation is excessively deep and possibly infinite.(2589)” in this case) but its behavior gets possibly chaotic. I describe here some specific experiences that I have made. Be warned in case you try to construct complex types.

You might suspect that for type ObjType = {v: ..., x: ...} the two variables const v1: ObjType = {v: ..., x: ...}; and const v2 = {...v1, x: v1.x}; are guaranteed to be of the same type. Not so in TypeScript.

type Liberal = { v: string, x: 0 | 1 };
type Restrictive = { v: string, x: 1 };
type LiberalEnhanced = { v: string, u: number, x: 0 | 1 };
type RestrictiveEnhanced = { v: string, u: boolean, x: 1 };
type Merged = { v…

If you use conditional types, be aware of some surprising limitations of TS’s inference capabilities, as e.g. encountering an undocumented magic number 25

type IsOneOf<T, Union> =
true extends EqualsOneOfTheComponents<T, Union>
? true
: false;

Matthias Falk

Get the Medium app

A button that says 'Download on the App Store', and if clicked it will lead you to the iOS App store
A button that says 'Get it on, Google Play', and if clicked it will lead you to the Google Play store