iwantcoding.com
🔥 Daily 👥 Rooms 🏆 Top Log in Sign up

TS Utility Types

TypeScript ships a small standard library of utility types — pre-built type transformations you'd otherwise have to derive yourself.

The core dozen

UtilityEffect
Partial<T>All properties optional.
Required<T>All properties required.
Readonly<T>All properties readonly.
Pick<T, K>Subset by keys.
Omit<T, K>Drop keys.
Record<K, V>Build a dict type.
Exclude<T, U>Remove members from a union.
Extract<T, U>Keep matching members.
NonNullable<T>Strip null / undefined.
ReturnType<F>Type of F's return.
Parameters<F>Tuple of F's parameter types.
Awaited<T>Recursively unwrap Promise.

Examples

TS
type User = { id: number; name: string; email: string; password: string };

// API patch endpoint — every field optional
type UserPatch = Partial<User>;

// Public fields only
type PublicUser = Omit<User, 'password'>;

// Just the identifying parts
type UserId = Pick<User, 'id' | 'name'>;

// Drop nullable
type Defined = NonNullable<string | null | undefined>;     // string

// Map by id
type ById = Record<number, User>;

Function utilities

TS
async function load(id: number): Promise<User> { /* ... */ return {} as User; }

type LoadFn    = typeof load;
type LoadRet   = ReturnType<LoadFn>;   // Promise<User>
type LoadValue = Awaited<LoadRet>;     // User
type LoadArgs  = Parameters<LoadFn>;   // [number]

Combining them

TS
type Email     = NonNullable<User['email']>;            // string
type Mutable   = { -readonly [K in keyof T]: T[K] };

// Strip readonly + nullable, leave the shape
type Patchable<T> = Partial<{ -readonly [K in keyof T]: NonNullable<T[K]> }>;
Tip: Whenever you reach for a manual transformation like "this type but with field X optional", check if a utility already exists. The TypeScript team has done the work.

Example

Example
type User = { id: number; name: string; email: string };

type P  = Partial<User>;          // all optional
type R  = Required<User>;
type RO = Readonly<User>;
type PK = Pick<User, 'id' | 'name'>;
type OM = Omit<User, 'email'>;
type RT = Record<string, number>;

const u: P = { name: 'Ada' };
console.log(u);
Try it Yourself »

Exercise

Make every property optional with…

type P = <User>;

Test yourself

Q1. Drop a key with…
Q2. Recursively unwrap a promise with…
Q3. Make every property optional with…

Discussion

Loading…