What’s actually slowing this PC down?
Pick the symptom - the matching free tool is one click away.
Use extends to build a new TypeScript interface from an existing one and add members. If you redeclare an inherited property, its type must remain compatible with the base type: you may narrow a union safely, but you cannot weaken a guarantee or widen the property incompatibly.
How interface extension works
An interface that extends another inherits its members. The child can add properties and methods, and it can redeclare an inherited property only when the new declaration preserves compatibility with the base contract. See the TypeScript handbook’s guide to extending interfaces.
interface Base {
id: string | number;
}
interface WithStringId extends Base {
id: string;
label: string;
}
string is assignable to string | number, so every WithStringId still satisfies the base interface’s requirement for an id that is a string or number. The child makes that promise more specific. TypeScript compatibility is structural: member shapes and assignability determine whether types fit, rather than their names alone. The Type Compatibility handbook describes this model.
What makes a redeclared property compatible?
The child type must preserve what consumers of the base are entitled to expect. A narrower type can work when its values remain assignable to the base property type. Widening, changing requiredness, or otherwise allowing values that violate the base contract does not.
Free tools Windows power users keep installed
One-click scans. No signup required.
#1 Best Overall
Narrowing a union is valid
If the base accepts either a string or a number, a child may restrict the property to strings, as in the example above. A consumer that needs only the base contract can still safely use that child value as a string | number.
Widening a base property is not a valid override
interface Base {
id: string;
}
interface WithWiderId extends Base {
id: string | number; // incompatible
}
The child would allow a number, even though the base promises that id is a string. That breaks substitutability, so TypeScript reports an incompatible extension. The same principle applies to optionality: making a required property optional removes a guarantee made by the base.
Rank #2
- TypeScript implements a superset of syntax for strictly typed development, facilitating deep static analysis and enhanced development environment integration. The compiler translates source into standard script formats, ensuring parity across any runtime.
- TypeScript is ideal for front-end developers, full-stack engineers, and software architects who build large-scale web applications. It serves those looking to improve code excellence, reduce bugs through static checking, and maintain complex projects more.
- Lightweight, Classic fit, Double-needle sleeve and bottom hem
interface Base {
id: string;
}
interface WithOptionalId extends Base {
id?: string; // incompatible: Base requires id
}
These examples illustrate the handbook’s structural compatibility and extension rules; they are not a report of a newly run compiler test. For details on object members and extension conflicts, see Object Types.
When you need alternatives, use a union
If a property is meant to allow several kinds of value, declare that choice in the base type rather than trying to widen it in a child:
Quick wins for a faster PC:
Clear out junk files and repair common Windows errorsFree Scan →Scan for outdated or missing drivers - takes under a minuteDriver Scan →interface Base {
id: string | number;
}
If the alternatives have different shapes or guarantees, represent them as distinct variants, commonly with a discriminated union. An intersection is not a way to choose between types: it requires a value to satisfy both constituent types. For example, string & number cannot represent a value that is both a string and a number. The handbook explains this distinction in Object Types.
Extending multiple interfaces
A child can extend more than one interface when their inherited members can be reconciled:
interface HasId {
id: string;
}
interface HasLabel {
label: string;
}
interface Item extends HasId, HasLabel {
active: boolean;
}
If bases declare a same-name property with incompatible types, the combination cannot provide a coherent contract. Review the conflicting declarations and decide whether they should share a compatible type or instead be represented as separate variants. TypeScript documents multiple-base extension and conflict behavior in its interface guide and object types guide.
Extension, declaration merging, and module augmentation
These features can all affect interface shapes, but they solve different problems.
Best Value
- Extension: Define a new named interface with
extendswhen it is a related, more specific contract that inherits another interface’s members. - Declaration merging: Declare the same interface name in multiple places to have TypeScript combine the declarations. Repeated non-function properties must have the same type; same-name function members form overloads. See Declaration Merging.
- Module augmentation: Augment a named export’s declaration when you need to describe an extension to a module’s type. The official classes documentation notes limits: augmentation cannot add new top-level declarations or augment a default export. A type declaration also does not implement runtime behavior; the corresponding runtime change must exist separately.
Inherited index signatures and class types
Index signatures constrain named properties
If a base interface has a string index signature, named properties in a derived interface must have values compatible with the index signature’s value type. For example, a base that allows arbitrary string-keyed numbers cannot be extended with a named string-valued property without changing that underlying contract. If both kinds of values are intended, use an index signature whose value type permits both. See the TypeScript Interfaces documentation.
An interface can extend a class type
An interface may extend a class type to inherit its member types, but this does not inherit implementations. Private and protected members remain significant: an interface that includes them can be implemented only by that class or by a subclass in the relevant hierarchy. The Classes handbook covers this relationship.
Quick Recap
Choose the right type construct
| Goal | Use | Reason |
|---|---|---|
| Add fields to a reusable contract | interface Child extends Base |
Keeps the relationship explicit and avoids repeating inherited members. |
| Combine compatible contracts | interface Combined extends A, B |
Interfaces support multiple bases when inherited declarations can be reconciled. |
| Allow several value types for one property | A union in that property’s type | Extension preserves the base contract; an intersection requires both constituent types. |
| Describe a library type extension | Module augmentation, when the named export and module resolution support it | It augments an existing declaration but does not add runtime code. |
| Model unrelated alternatives | A discriminated union | Each variant can make its own guarantees without claiming that one is a subtype of another. |
Product prices and availability are accurate as of the date/time indicated and are subject to change. Any price and availability information displayed on Amazon at the time of purchase will apply.




