Le Declaration Merging est une caractéristique unique de TypeScript qui permet de combiner plusieurs déclarations avec les mêmes noms en une seule entité. Cela est dû à l'histoire de TypeScript en tant que typage sur JavaScript : de nombreuses bibliothèques tierces déclaraient des interfaces, des fonctions, des espaces de noms, et TypeScript devait permettre de les étendre sans modifier le code source de la bibliothèque.
Dans des API complexes et lors de la typage de bibliothèques JS tierces, il peut être nécessaire de diviser la responsabilité — par exemple, étendre les types d'un module, ajouter des champs à une interface, combiner des noms. Cependant, la plupart des langages ne prennent pas en charge une telle combinaison de déclarations.
TypeScript permet de fusionner (merge) les déclarations d'interfaces, d'espaces de noms, de fonctions, de classes avec des noms identiques, ce qui rend l'API flexible pour l'extension. Il est utilisé pour étendre des types tiers, ajouter des méthodes personnalisées aux bibliothèques, ainsi que pour organiser du code modulaire.
Exemple de code :
// interfaces merging interface User { id: number; } interface User { name: string; } const u: User = { id: 1, name: "Jack" }; // namespace + function merging function greet() { return "Hi!"; } namespace greet { export function loud() { return "HI!"; } } greet(); // "Hi!" greet.loud(); // "HI!"
Caractéristiques clés :
Peut-on fusionner des type alias de manière similaire aux interfaces ?
Non, les type alias ne peuvent pas être fusionnés. En essayant de déclarer plusieurs types avec le même nom, une erreur de compilation se produira.
type T = { a: string }; type T = { b: number }; // Erreur
TypeScript insérera-t-il des champs d'interface/espace de noms dans un ordre aléatoire ?
La structure fusionnée est toujours construite dans l'ordre de la déclaration — si des noms de propriétés identiques existent, la dernière déclaration "l'emporte".
Les méthodes d'une interface sont-elles fusionnées en une seule fonction ?
Non, les méthodes avec des noms identiques dans différentes interfaces ne fusionnent pas en une seule fonction — si les signatures coïncident, TypeScript n'autorise pas et n'autorise pas l'implémentation des "deux" variantes.
Une entreprise définit l'interface globale Window deux fois avec des champs différents et des types différents pour un champ avec le même nom. Lors de la compilation, le compilateur ne détecte pas le problème, mais au moment de l'exécution, un conflit de types imprévu apparaît.
Avantages :
Inconvénients :
Un fichier d.ts est écrit pour une bibliothèque tierce, où l'interface de l'API est étendue par des modules séparés sans changer la bibliothèque elle-même, toutes les extensions sont documentées, la politique de nommage est décrite dans le Wiki.
Avantages :
Inconvénients :