Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Can you make a smaller, more restricted type from an existing type?

Assuming I have this type declaration:

type Foo = 'a' | 'b' | 'c';
type Bar = 'a' | 'b' ;

Is it possible to express Bar as a subset of Foo ?

I understand it's always possible to express Foo as a superset of Bar, but in my case the other way around would feel more in line with the domain.

like image 799
phtrivier Avatar asked Mar 03 '23 17:03

phtrivier


2 Answers

You simply have to use the Exclude pre-defined conditional type:

type Foo = 'a' | 'b' | 'c';
type Bar = Exclude<Foo, 'c'>;

const Bar = 'a';

Do note that the following works fine, even if it may not feel right at first glance:

type Bar = Exclude<Foo, 'd'>

See playground.


You can also combine it with index types for interesting purposes:

type Foo = 'a' | 'b' | 'c';
type AnObject = { c: boolean }
type Bar = Exclude<Foo, keyof AnObject>

const myVar: Bar = "a";
like image 137
Kyll Avatar answered May 18 '23 13:05

Kyll


E.g.

type Bar = Exclude<Foo, 'c'>

(documented in https://www.typescriptlang.org/docs/handbook/advanced-types.html#predefined-conditional-types)

like image 21
Alexey Romanov Avatar answered May 18 '23 13:05

Alexey Romanov