TypeScript Mapped Types with Utility Types
Learn how mapped types and utility types work together. Examples for creating custom transformations using keyof, in, and conditional types.
Detailed Explanation
Mapped Types + Utility Types
Mapped types iterate over the keys of a type and transform each property. Combined with utility types, they enable powerful custom transformations.
Basic Mapped Type
type Nullable<T> = {
[K in keyof T]: T[K] | null;
};
interface User {
name: string;
age: number;
}
type NullableUser = Nullable<User>;
// { name: string | null; age: number | null }
Key Remapping (TypeScript 4.1+)
type Getters<T> = {
[K in keyof T as `get${Capitalize<string & K>}`]: () => T[K];
};
type UserGetters = Getters<User>;
// { getName: () => string; getAge: () => number }
Filtering Keys with Exclude
type PublicKeys<T> = {
[K in keyof T as K extends `_${string}` ? never : K]: T[K];
};
interface Service {
getData(): string;
_internal(): void;
_cache: Map<string, unknown>;
name: string;
}
type PublicService = PublicKeys<Service>;
// { getData(): string; name: string }
Conditional Property Types
type ReadonlyArrays<T> = {
[K in keyof T]: T[K] extends any[] ? readonly T[K][number][] : T[K];
};
interface State {
items: string[];
count: number;
tags: number[];
}
type ImmutableState = ReadonlyArrays<State>;
// { items: readonly string[]; count: number; tags: readonly number[] }
Building Custom Utility Types
// Make specific keys optional
type PartialBy<T, K extends keyof T> = Omit<T, K> & Partial<Pick<T, K>>;
// Make specific keys required
type RequiredBy<T, K extends keyof T> = Omit<T, K> & Required<Pick<T, K>>;
// Make specific keys readonly
type ReadonlyBy<T, K extends keyof T> = Omit<T, K> & Readonly<Pick<T, K>>;
Use Case
Use mapped types with utility types when the built-in utilities are not enough and you need custom property transformations. Common for building reusable type utilities in shared libraries, form libraries, state management tools, and API clients.
Try It — TypeScript Utility Types
Related Topics
Composing Multiple TypeScript Utility Types
Advanced Patterns
TypeScript Pick<T, K> Utility Type Explained
Object Types
TypeScript Omit<T, K> Utility Type Explained
Object Types
TypeScript Record<K, T> Utility Type Explained
Object Types
TypeScript String Manipulation Utility Types Explained
String Types
TypeScript Exclude<T, U> vs Extract<T, U> Explained
Union Types