Les nœuds DOM ne sont pas la chaîne HTML que vous avez envoyée.
Le DOM n’est pas la chaîne HTML que vous avez envoyée. Les arbres de parsing, les NodeLists dynamiques et les reflows expliquent pourquoi une approche basée sur les chaînes de caractères échoue dans les interfaces utilisateur JavaScript et React.
Sources: The DOM Is Not Your HTML: The Difference Every Frontend Developer Should Understand
Lorsque le code balisé est envoyé au navigateur, il définit la structure initiale de la page. Un document peut commencer par un titre simple :
<h1>Hello</h1>
Après chargement, JavaScript peut localiser ce titre et remplacer son texte :
document.querySelector("h1").textContent = "Hello World";
L’écran affiche alors :
<h1>Hello World</h1>
Cela peut donner l’impression que le fichier HTML lui-même a été réécrit. Ce n’est pas le cas. Le fichier sur le serveur conserve toujours le titre original. JavaScript a modifié le modèle en temps réel de la page dans le navigateur — le DOM. Séparer le code balisé source de ce modèle en temps réel permet de mieux comprendre de nombreux comportements de JavaScript.
HTML est un document. Le DOM est une représentation en temps réel.
HTML est le code balisé que vous écrivez, par exemple :
<body>
<h1>Hello</h1>
<button>Click me</button>
</body>
Le navigateur analyse ce document pour en créer une structure en mémoire. Cette structure est le Document Object Model. Un aperçu simplifié du processus est le suivant :
HTML
│
│ browser parses
▼
DOM
│
├── body
│ ├── h1
│ └── button
Le DOM n’est pas simplement une copie textuelle de votre HTML. C’est un document structuré et programmable. C’est ce que JavaScript manipule.
Alors, qu’est-ce que JavaScript modifie réellement ?
Commencez par :
<h1 id="title">Hello</h1>
Puis exécutez :
const title = document.querySelector("#title");
title.textContent = "Welcome";
Le script trouve le nœud DOM et met à jour son texte. L’arbre en temps réel représente désormais :
<h1 id="title">Welcome</h1>
Le code HTML original n’a pas été réécrit. Si le markup provient d’un serveur ou d’un fichier statique, cette source contient toujours :
<h1 id="title">Hello</h1>
La différence est mineure mais cruciale : modifier le DOM n’est pas identique à éditer le code HTML source.
Voici un moyen simple de voir la différence
Ouvrez une page et modifiez quelque chose depuis la console :
document.querySelector("h1").textContent = "Changed!";
La page visible se met à jour immédiatement. Comparez le DOM en temps réel :
<h1>Changed!</h1>
avec le code HTML source original :
<h1>Hello</h1>
Ils peuvent différer car le navigateur travaille avec son DOM en temps réel.
Le DOM est plus que ce que vous avez écrit à l’origine
Supposons que le marquage commence ainsi :
<ul id="users">
<li>John</li>
</ul>
JavaScript peut ajouter un autre élément :
const list = document.querySelector("#users");
const item = document.createElement("li");
item.textContent = "Sarah";
list.appendChild(item);
L’arbre en temps réel contient maintenant :
ul
├── li "John"
└── li "Sarah"
« Sarah » n’apparaissait jamais dans le fichier original. Le navigateur n’a pas besoin d’un document source réécrit ; le script a modifié le DOM en temps réel. Cette capacité est à l’origine des sites interactifs.
Le DOM est un arbre
« Modèle d’objets » semble plus complexe que l’idée ne l’est en réalité. Au niveau le plus simple, le DOM est un arbre de nœuds. Étant donné :
<main>
<h1>Hello</h1>
<p>Welcome!</p>
</main>
le navigateur crée une structure à peu près comme celle-ci :
Document
│
└── main
├── h1
│ └── "Hello"
│
└── p
└── "Welcome!"
C’est la structure en arbre qui permet aux scripts de parcourir des relations telles que :
element.parentElement
element.children
element.nextElementSibling
Vous n’analysez pas un fichier de texte brut ; vous naviguez dans un arbre structuré.
Et le DOM peut changer
L’HTML source est généralement le document initial. L’arbre en mémoire reste modifiable pendant l’exécution. Les scripts peuvent allouer des nœuds :
const button = document.createElement("button");
attribuer des attributs :
button.setAttribute("disabled", "");
modifier le contenu :
button.textContent = "Loading...";
et insérer le nœud :
document.body.append(button);
L’arbre évolue au fur et à mesure que l’application s’exécute, c’est pourquoi les interfaces interactives n’ont pas besoin d’un téléchargement complet de l’HTML pour chaque petite modification.
Mais il y a encore une chose que les développeurs confondent souvent
L’inspection d’une page peut révéler de l’HTML qui n’était jamais présent dans la source originale. Un script peut créer :
<div class="notification">
Saved successfully
</div>
Vous n’êtes pas l’auteur de ce nœud, mais DevTools peut le afficher dans le panneau Elements car ce panneau reflète le DOM. View Source peut omettre complètement ce nœud.
View Source et Inspect Element ne correspondent donc pas nécessairement. Une raison fréquente est que JavaScript modifie le DOM après le chargement initial de l’HTML.
Pourquoi est-ce important pour les développeurs frontend ?
Beaucoup de comportements frontend deviennent plus clairs une fois que le modèle mental passe de « JavaScript modifie l’HTML » à « JavaScript modifie le DOM ». Cette approche explique des API telles que :
element.classList.add("active");
element.remove();
element.textContent = "Loading...";
element.append(newElement);
Ces appels agissent sur la structure du document en temps réel. Le navigateur utilise ensuite cet arbre mis à jour pour afficher l’écran.
Et React ?
Cette même distinction est utile pour apprendre React. Vous pourriez écrire :
return <h1>Hello</h1>;
JSX n’est pas littéralement le DOM. C’est une syntaxe qui décrit l’interface utilisateur. React décide de la manière dont cette description doit être reflétée dans le DOM réel. Comprendre le DOM avant de s’immerger dans les abstractions des frameworks rend la rendu, la réconciliation, les refs et les mises à jour du DOM moins mystérieux.
Vous n’avez pas besoin de connaître tous les détails internes. Gardez à l’esprit ce flux de travail :
HTML
↓
Browser parses it
↓
DOM
↓
JavaScript can modify it
↓
Browser updates the rendered page
Les frameworks ajoutent des couches supplémentaires, mais le DOM du navigateur reste la base.
Une erreur courante
Les développeurs traitent parfois une mutation du DOM comme une modification permanente de l’HTML original. Ce n’est pas le cas. Par exemple :
document.body.innerHTML = "<h1>New page</h1>";
Cette affectation peut remplacer la structure en temps réel actuelle, mais elle ne réécrit pas le fichier HTML sur le serveur. Une mise à jour recharge le document depuis sa source. À moins que le changement n’ait été enregistré et qu’un nouveau HTML n’ait été généré, le document d’origine revient. Cet écart sépare l’état en temps de exécution du contenu source.
Le modèle mental à retenir
Évitez de confondre les idées :
HTML = DOM
Préférez un flux proche de :
HTML
│
│ parsed by browser
▼
DOM
│
│ modified by JavaScript
▼
Updated DOM
│
│ used during rendering
▼
What the user sees
Considérez l’HTML comme le document source écrit par l’auteur. Considérez le DOM comme l’arbre modifiable du navigateur construit à partir de ce source. Les scripts modifient cet arbre ; l’affichage suit ce que l’arbre contient actuellement.
Conclusion finale
Ne confondez pas le DOM avec le fichier HTML. Le marquage est ce que vous écrivez ; le modèle d’objets, c’est ce que le navigateur maintient actif tant que l’onglet est ouvert. Grâce à cette séparation, plusieurs comportements deviennent évidents : pourquoi les scripts peuvent ajouter et supprimer des nœuds, pourquoi querySelector() fonctionne, pourquoi textContent met à jour ce que vous voyez, pourquoi les outils de développement peuvent afficher des nœuds que vous n’avez jamais créés, pourquoi l’arbre en temps réel peut différer de la source, et pourquoi React touche finalement toujours le DOM.
Le changement de perspective utile est simple : vous écrivez du HTML, le navigateur construit le DOM, et JavaScript modifie ce dernier. Une fois cette idée comprise, le DOM cesse de sembler être une API opaque pour ressembler à ce qu’il est réellement : la représentation en temps réel de la page par le navigateur.