I need to define a Mapped type that specifies a field
named status
which can be either a string or the string value ready
:
This example works as expected:
export type ValidServiceState = HasReady<{ status: "ready" }>;
The following should work, but it currently results in mapping to 'never' due to extra values in the union.
// this should be good because ready is one of the allowable values
export type ValidServiceState = HasReady<{ status: "ready" | "bananas" }>;
However, this scenario correctly maps to never
:
// should be never
export type InvalidServiceState = HasReady<{ status: "not_ready" | "something_else_that_is_not_ready" }>;
I attempted the following approach:
type HasReady<S extends { status: string } > = S extends { status: "ready" }
? S
: never;
But this implementation only allows for a strict { status: "ready}
Below is a consolidated version of the code snippet:
type HasReady<S extends { status: string }> = S extends { status: "ready" }
? S
: never;
// this should be good because ready is one of the allowable values
export type ValidServiceState = HasReady<{ status: "ready" | "bananas" }>;
// never
export type InvalidServiceState = HasReady<{ status: "not_ready" }>;
Here is a handy playground link for the above code