TypeScript Object Types
Object types describe the shape of an object's properties, letting TypeScript check that the right keys and value types are present wherever that object is used.
Defining an Object Type
An object type lists property names and the type of value each property should hold. You can write it inline or extract it into a reusable type alias or interface.
Inline vs Named Object Types
// Inline object type
function printUser(user: { name: string; age: number }) {
console.log(`${user.name} is ${user.age}`);
}
// Named, reusable object type
type User = {
name: string;
age: number;
};
function printUserNamed(user: User) {
console.log(`${user.name} is ${user.age}`);
}Optional and Readonly Properties
Properties can be marked optional with a question mark, meaning the key may be omitted entirely. Properties can also be marked readonly, meaning they can be set when the object is created but not reassigned afterward.
Optional and Readonly Members
type Product = {
readonly id: string;
name: string;
description?: string;
};
const item: Product = { id: "p1", name: "Keyboard" };
// item.id = "p2"; // Error: Cannot assign to 'id' because it is a read-only property
item.description = "Mechanical keyboard"; // fine, optional property being setNested Object Types
Object types can contain other object types as property values, letting you model structured, nested data such as an address inside a user record.
Nesting Object Types
type Address = {
street: string;
city: string;
postalCode: string;
};
type Customer = {
name: string;
address: Address;
};
const customer: Customer = {
name: "Jordan",
address: { street: "12 Elm St", city: "Austin", postalCode: "73301" },
};Index Signatures
Sometimes you don't know property names in advance, only their pattern — for example, a dictionary of scores keyed by player name. Index signatures let you type these dynamic-key objects.
Index Signature Example
type ScoreBoard = {
[playerName: string]: number;
};
const scores: ScoreBoard = {};
scores["Amara"] = 10;
scores["Lee"] = 7;
// scores["Lee"] = "seven"; // Error: must be a number- Use plain object types for known, fixed sets of properties.
- Use optional (?) for properties that may be absent.
- Use readonly for properties that must not change after creation.
- Use index signatures for dictionary-like, dynamically-keyed objects.
- Prefer extracting a type alias once an object shape is used in more than one place.
Object Types vs Excess Property Checks
Realistic Use Case: Typing an API Response
Object types shine when modeling data coming back from an API, ensuring every place in your code that consumes the response agrees on its shape.
Typing a Fetch Response
type ApiUser = {
id: number;
username: string;
email: string;
isActive?: boolean;
};
async function fetchUser(id: number): Promise<ApiUser> {
const response = await fetch(`/api/users/${id}`);
const data: ApiUser = await response.json();
return data;
}Exercise: TypeScript Object Types
How do you annotate a parameter as an object with a name string and age number?