What Are Utility Types?
Utility types are built-in generic types provided by TypeScript to perform common operations on types. They are used in conjunction with the keyof
and typeof
keywords to create new types based on existing ones. Here are some of the most commonly used utility types.
1. Partial<T>
The Partial<T>
utility type allows you to create a new type with all properties of T
, but they are all optional. This can be handy when you want to make some properties of an object optional without explicitly specifying each one.
Example:
interface Person {
name: string;
age: number;
}
type PartialPerson = Partial<Person>;
const partialPerson: PartialPerson = {};
// valid, no properties required
const partialPerson2: PartialPerson = { name: "Alice" };
// valid, name is provided
const partialPerson3: PartialPerson = { name: "Bob", age: 30 };
// valid, both name and age are provided
2. Required<T>
The Required<T>
utility type does the opposite of Partial<T>
. It makes all properties of T
required.
Example:
interface Person {
name?: string;
age?: number;
}
type RequiredPerson = Required<Person>;
const requiredPerson: RequiredPerson = { name: "Alice", age: 25 };
// valid, both name and age are required
const requiredPerson2: RequiredPerson = {};
// Error: Property 'name' is missing in type '{}' but required in type 'RequiredPerson'.
3. Readonly<T>
The Readonly<T>
utility type creates a new type where all properties of T
are read-only, preventing you from accidentally modifying them.
Example:
interface Point {
x: number;
y: number;
}
type ReadonlyPoint = Readonly<Point>;
const point: ReadonlyPoint = { x: 10, y: 20 };
// valid
point.x = 5;
// Error: Cannot assign to 'x' because it is a read-only property.
4. Record<K, T>
The Record<K, T>
utility type creates an object type with keys of type K
and values of type T
.
Example:
type Car = "sedan" | "suv" | "hatchback";
type CarInfo = Record<Car, number>;
const carInfo: CarInfo = {
sedan: 4,
suv: 5,
hatchback: 3,
};
5. Pick<T, K>
The Pick<T, K>
utility type creates a new type by picking only the specified properties K
from T
.
Example:
interface Person {
name: string;
age: number;
address: string;
}
type PersonInfo = Pick<Person, "name" | "age">;
const person: PersonInfo = {
name: "Alice",
age: 30,
};
6. Omit<T, K>
The Omit<T, K>
utility type creates a new type by omitting the specified properties K
from T
.
Example:
interface Person {
name: string;
age: number;
address: string;
}
type PersonWithoutAddress = Omit<Person, "address">;
const person: PersonWithoutAddress = {
name: "Alice",
age: 30,
};
Combining Utility Types
One of the powerful aspects of utility types is that you can combine them to create more complex types. Let's look at an example where we combine Partial
and Readonly
:
interface Person {
name: string;
age: number;
}
type PartialReadOnlyPerson = Partial<Readonly<Person>>;
const person: PartialReadOnlyPerson = {
name: "Alice",
};
Happy coding! 🚀👨💻👩💻
Top comments (0)