Type guards: isDefined, isString, isOneOf
Write three checks after which TypeScript narrows the value's type.
isDefined(value): not null and not undefined; [1, null, 2].filter(isDefined) should give number[], and 0 and "" are values too. isString(value): a string. isOneOf(values) returns a check for one of the listed values: after isOneOf(["red", "green"] as const)(c) the type of c is "red" | "green".
Ctrl+Enter runs the tests. Tab indents; to leave the editor with the keyboard, press Esc and then Tab. Your code is saved in this browser.
Tests (6)
Type tests are checked by the TypeScript compiler in strict mode. Expect<Equal<A, B>> passes when the types match exactly, and // @ts-expect-error passes when the next line does not compile. The first run downloads the compiler, so it takes a few seconds.
- types
const xs = [1, null, 2, undefined].filter(isDefined); type _ = Expect<Equal<typeof xs, number[]>>;
- types
const v: unknown = 'x'; if (isString(v)) { type _ = Expect<Equal<typeof v, string>>; }
- types
const isColor = isOneOf(['red', 'green'] as const); const c: unknown = 'red'; if (isColor(c)) { type _ = Expect<Equal<typeof c, 'red' | 'green'>>; }
expect([1, null, 2, undefined, 0, ''].filter(isDefined)).toEqual([1, 2, 0, '']);
expect(isString('a')).toBe(true); expect(isString(1)).toBe(false); expect(isString(null)).toBe(false);
const isColor = isOneOf(['red', 'green']); expect(isColor('red')).toBe(true); expect(isColor('blue')).toBe(false);