In the current state of Typescript, there is no concept of exact types apart from object literals (with a special exception explained later). This means that every object conforming to an interface can have additional properties that are not defined in the interface itself.
For example, consider this object:
{
command: 34234,
children: [{ foo: 'qwerty' }, { asdf: 'zxcv' }],
}
This object satisfies both the Type1
and Type2
interfaces because it contains all properties specified by each interface (command
and children
).
It's important to note that while exact typing is not supported for most cases, Typescript does enforce exact types for object literals only:
export const unionType: Type1 = {
command: 34234,
children: [{ foo: 'qwerty' }, { asdf: 'zxcv' }], // Will raise an error here
};
export const unionType: Type2 = {
command: 34234, // Will raise an error here
children: [{ foo: 'qwerty' }, { asdf: 'zxcv' }],
};
The code snippet above demonstrates how object literals are treated differently. In contrast, when dealing with variables instead of object literals, exact typing rules do not apply:
const someVar = {
command: 34234,
children: [{ foo: 'qwerty' }, { asdf: 'zxcv' }]
};
const: Type1 = someVar // This assignment is permitted since it involves a variable, not an object literal