When working with objects, you sometimes want to prevent accidental changes to certain properties. TypeScript’s readonly
modifier helps you lock properties so they can’t be reassigned after creation.
1. The readonly
Modifier in Interfaces or Type Aliases
You can add readonly
directly to each property:
type User = {
readonly name: string;
readonly age: number;
};
-
name
andage
are both read-only. - Once a
User
object is created, these properties cannot be reassigned.
Example:
const user: User = {
name: "Safal",
age: 10,
};
user.age = 12; // ❌ Error: Cannot assign to 'age' because it is a read-only property
TypeScript’s compiler enforces immutability at compile time.
(At runtime, it’s still a normal JavaScript object, but TypeScript stops you from writing code that would mutate it.)
2. Readonly<T>
Utility Type
Instead of writing readonly
on every property, TypeScript provides a built-in utility type:
type User1 = {
name: string;
age: number;
};
const user1: Readonly<User1> = {
name: "Safal",
age: 10,
};
Here, Readonly<User1>
creates a new type identical to User1
, but with all properties marked as readonly
.
It’s equivalent to:
type ReadonlyUser1 = {
readonly name: string;
readonly age: number;
};
Any attempt to reassign:
user1.name = "New Name"; // ❌ Error: Cannot assign to 'name' because it is a read-only property
3. When to Use readonly
- Immutable data models: Prevent unintended mutations in configuration objects or Redux state.
- API boundaries: When exposing data to other parts of the app that should not be modified.
- Functional programming patterns: Enforce immutability by design.
4. Key Points to Remember
-
Compile-time only:
readonly
is enforced by TypeScript’s type checker. JavaScript doesn’t freeze the object automatically.
- If you need runtime immutability, you can also use
Object.freeze()
.-
Shallow:
readonly
only applies to the top-level properties, not nested objects.
-
Shallow:
Example:
type Nested = {
readonly info: { value: number };
};
const x: Nested = { info: { value: 1 } };
x.info.value = 2; // ✅ Allowed, because `value` is not marked readonly
Quick Comparison
Feature | Example | Effect |
---|---|---|
Property modifier | readonly name: string; |
Mark individual properties as immutable |
Utility type | Readonly<User> |
Make all properties of a type read-only |
Summary
Use readonly
when you want TypeScript to guarantee immutability of object properties.
- Add
readonly
directly to specific properties for fine-grained control. - Use the
Readonly<T>
utility to lock down an entire type at once.
This helps keep your data structures predictable and protects against accidental mutation in large codebases.
Top comments (0)