Quand un site WordPress se met à “agir bizarrement”, la première piste que j’inspecte n’est pas le backend, mais la page telle qu’elle est réellement servie. Un malware WordPress a rarement besoin de toucher à l’ensemble du CMS pour faire des dégâts. Il suffit parfois de quelques lignes de code qui s’accrochent à une portion de template, ou d’un chargement de script externe, discret, qui se déclenche au bon moment, pour rediriger, déposer des publicités, ou tenter une prise de contrôle côté visiteur.
Dans ce type d’incident, un bon réflexe consiste à vérifier le chargement de scripts externes suspects. Ce travail paraît simple, mais il demande de la méthode: regarder le bon type de pages, comparer ce qui devrait se charger, distinguer un script légitime d’un script “look-alike”, et surtout comprendre d’où vient l’injection.
Les symptômes qui pointent vers des scripts externes
Les infections “par script” se manifestent souvent par des effets qui semblent venir du navigateur, alors que https://gardewp.fr/nettoyage-malware-wordpress/ l’origine est côté serveur. On voit par exemple:
- Des redirections inattendues après clic, ou parfois seulement sur certains navigateurs. Des bannières ou pop-ups qui n’existent pas en temps normal. Une lenteur soudaine sur des pages précises, avec des requêtes réseaux qui montent en charge. Un changement de contenu “après chargement” (script qui modifie le DOM), sans que le HTML initial ne ressemble à la page normale. Des scripts qui ne se chargent que sur une géolocalisation, ou seulement lorsque l’utilisateur a certains cookies.
J’ai déjà vu un site où la page d’accueil “semblait intacte” dans WordPress, mais où, en regardant l’onglet Réseau des DevTools, on voyait une requête vers un domaine qui n’avait rien à faire là. Le HTML envoyé par le serveur contenait une balise
Définir le périmètre avant de diagnostiquer
Avant de fouiller, je fixe trois repères, sinon on se noie vite:
Quelle page est concernée: page d’accueil, articles, pages produit, pages d’admin accessibles publiquement, etc. Dans quel contexte ça arrive: uniquement sur mobile, uniquement sur un navigateur précis, seulement après un clic, ou automatiquement à l’ouverture. Si le comportement diffère selon l’utilisateur: moi connecté ou non, avec cookies existants ou vierges, première visite ou visite récurrente.L’intérêt de cette étape est simple: elle aide à distinguer une simple publicité tierce (parfois variable) d’une injection persistante. Un vrai incident de sécurité a tendance à être reproductible, même si le déclenchement est conditionnel.
Vérifier le HTML servi: la première preuve
Le point de départ est la source HTML effectivement renvoyée. Dans beaucoup https://gardewp.fr/ d’infections, le script externe est injecté dans le rendu côté serveur, donc on peut le repérer en inspectant la page.
Sur une page “suspecte”, ouvrez les DevTools (F12), puis:
- Cherchez des balises supplémentaires dans le HTML. Regardez les attributs src et les chaînes de caractères associées. Surveillez aussi les scripts inline, surtout ceux qui contiennent du chiffrement basique, du décodage de base64, ou des appels à des fonctions obfusquées.
Le piège, c’est que certaines infections ne se voient pas au premier coup d’œil parce qu’elles construisent dynamiquement l’élément dans le navigateur. Dans ce cas, l’outil Réseau aide davantage.
Ce que j’attends de scripts “propres” sur WordPress
Un WordPress sain charge, en général, des scripts depuis des sources cohérentes avec votre stack. Typiquement, vous avez:
- Des fichiers internes (du thème, des plugins, du core). Des dépendances standard (selon configuration) hébergées sur le même domaine ou des CDN que vous avez effectivement choisis. Des scripts marketing si vous utilisez réellement un tag manager, une analytics, un pixel publicitaire.
Si vous voyez un domaine externe que vous ne reconnaissez pas, ou un sous-domaine “bizarre” imitant un service connu, c’est un drapeau rouge. Et si ce chargement n’est pas présent en comparant à une sauvegarde propre, c’est encore plus parlant.
Observer l’onglet Réseau: le script qui “fait le coup”
Même si le HTML semble propre, un script injecté peut déclencher des requêtes ensuite. L’onglet Réseau permet de remonter la chronologie.
Je procède souvent ainsi:
Je recharge la page, cache vidé si possible, en désactivant l’extension “anti-tracking” si elle masque trop de choses. Je filtre sur “Script” dans le panneau Réseau. Je regarde les requêtes externes: domaine, chemin, taille, type de contenu, statut (200, 404, etc). Je vérifie si une requête inconnue apparaît à un moment précis, juste avant le comportement malveillant.Un détail utile: les scripts “chargés puis exécutés” peuvent être livrés sous forme de fichier. Parfois, ils ont des noms génériques, ou un suffixe étrange. D’autres fois, ils renvoient du contenu qui a l’air compressé ou encodé. Sans tomber dans la paranoïa, le principe reste: si ce domaine n’est pas attendu, il mérite d’être investigué.
Identifier l’initiateur: depuis quel script ça part?
Dans l’outil, en sélectionnant une requête, on peut souvent voir “Initiator” ou des éléments associés. L’objectif est de répondre à une question très concrète: est-ce que c’est le thème, un plugin, ou un script inline qui injecte ensuite.
Cette étape réduit drastiquement l’espace de recherche. Si l’initiator est un fichier de thème ou un plugin connu, je sais où regarder. Si l’initiator pointe vers un script inline anormal, je reviens au HTML et je repère la balise incriminée.
Reconnaître les signaux d’un script externe suspect
Tout script externe n’est pas malveillant. Un CDN peut être légitime. La difficulté consiste à distinguer un ajout normal d’une intrusion.
Voici les signaux que j’ai le plus souvent rencontrés lors de nettoyages:
- Le script vient d’un domaine jamais utilisé, ou dont le format n’a aucun sens pour votre projet (beaucoup de chiffres, sous-domaines multiples, chemins incohérents). Le script n’est chargé que sur certaines pages, alors que votre configuration s’attend à un comportement uniforme. Le script est injecté mais n’expose pas d’attributs attendus (par exemple, pas de balises que votre tag manager n’aurait pas créées). Le script est “trop discret”: il fait une requête vers un autre service, puis disparaît. Le vrai effet peut être dans la seconde requête. Le contenu du script est fortement obfusqué, avec des chaînes encodées, des calculs sur caractères, et des appels à des fonctions “génériques”.
Une fois, un script externe semblait inoffensif au début, mais son contenu construisait une URL à partir de fragments, puis faisait un fetch vers un domaine différent. Ce n’est pas toujours visible à la surface, mais en inspectant le code renvoyé, on voit des motifs typiques d’obfuscation.
D’où vient l’injection sur WordPress: les endroits classiques
Une infection qui ajoute un chargement de script externe passe souvent par des points d’insertion fréquents. Sans supposer, j’inspecte ces zones dans l’ordre où elles ont le plus de chances d’avoir été touchées.
Le core et les fichiers “public” ne sont pas les seuls coupables. Les thèmes et les plugins restent des cibles majeures, surtout lorsqu’un plugin est vulnérable, abandonné, ou qu’une mise à jour a été manquée.
En pratique, je cherche:
- Des modifications dans wp-content/themes/... et wp-content/plugins/..., surtout au niveau des fichiers de template qui s’exécutent sur le front. Un ajout dans des fichiers “parent” comme header.php, footer.php, ou dans des templates spécifiques utilisés par certains types de pages. Des ajouts côté fonctions, souvent dans functions.php du thème, avec des conditions liées aux pages. Des modifications de fichiers qui ne devraient pas être touchés mais qui contiennent soudain du code de rendu ou d’injection.
Selon l’historique du site, il peut aussi y avoir une injection dans une configuration d’éditeur, ou dans un comportement lié à un formulaire, mais l’étape scripts externes sert justement à remonter au point d’insertion.
Méthode de comparaison: ce qui aide vraiment
Le nettoyage est beaucoup plus rapide quand on compare “avant” et “après”. Une sauvegarde propre, même ancienne, ou un environnement de staging, fait gagner des heures.
Si vous avez:
- une sauvegarde du dossier WordPress, ou un export de l’état précédent, ou un site miroir sur staging,
Alors je compare les fichiers et je repère les différences. Sans tomber dans un audit trop théorique, je cible surtout les fichiers qui apparaissent comme source de l’initiation dans les DevTools.
Si vous n’avez pas de sauvegarde, vous pouvez quand même établir un repère en testant une autre page, ou en comparant au rendu sur un domaine censé être identique. L’idée reste la même: comprendre ce qui change.
Cas fréquent: script externe ajouté via un champ “dynamique”
Parfois l’injection ne passe pas par un fichier PHP modifié, mais par une donnée. Un plugin peut stocker un contenu dans la base, et le réinjecter dans le rendu. Le résultat ressemble à une intrusion dans les templates, mais l’agent est une donnée contaminée.
C’est une source de confusion. Dans ce scénario:
- Le HTML final contient un script externe. Le fichier PHP modifié n’est peut-être pas évident à trouver. En inspectant la page, on voit une portion qui ressemble à un “custom code” (par exemple dans un champ de configuration) ou à une zone ajoutée par un builder.
C’est pour ça que la vérification du chargement de scripts externes ne suffit pas à elle seule. Elle vous dit “quoi” et parfois “quand”. Ensuite, il faut remonter au “d’où”, soit en identifiant l’initiateur, soit en traçant les données.
Traquer la source dans le code: de la requête à la ligne exacte
Une fois que vous avez identifié le domaine suspect (ou l’une des requêtes), vous pouvez remonter. Le workflow que j’utilise ressemble à une enquête.
Je note le domaine exact et, si possible, le chemin de l’URL. Je fais une recherche dans le dossier wp-content sur des morceaux uniques du domaine ou du chemin. Même si l’infection obfusque, il reste parfois des segments reconnaissables. Je vérifie aussi les scripts inline visibles dans la source, et je cherche des chaînes qui correspondent aux fragments de l’URL.Ce n’est pas toujours parfait. Il peut y avoir de l’encodage et des variables. Mais souvent, au moins une partie du domaine est stockée en clair dans un fichier ou dans la base.
Attention à ne pas casser le site en investiguant
Le test de suppression des scripts dans le HTML côté navigateur est tentant, mais ce n’est pas un correctif. Vous pourriez “masquer” le symptôme et rater l’infection persistante.
Si je dois faire des tests rapides, je préfère:
- du staging quand c’est possible, ou une procédure courte: retirer temporairement le chargement suspect via un patch local, puis recharger pour voir si la requête disparaît, sans oublier de revenir à l’état précédent une fois la piste validée.
Le but est de valider une hypothèse, pas de laisser le site dans un état incohérent.
Séparer le vrai signal du bruit: plugins, tags, et CDN
Un point délicat lors d’un nettoyage virus WordPress est la différence entre “script externe suspect” et “script externe légitime mais non maîtrisé”.
Beaucoup de sites finissent avec un patchwork de plugins de tracking, de connecteurs, et de scripts que personne ne sait expliquer. Le site est peut-être sain, mais vous avez trop de dépendances externes, et elles se ressemblent.
Donc, je fais une règle simple: si le domaine n’est pas attendu, je le traite comme suspect jusqu’à preuve du contraire. Cela veut dire vérifier:
- Si le domaine figure dans la configuration d’un plugin (dans ses réglages). Si le domaine apparaît dans les pages normales du site, ou uniquement dans les pages “ciblées”. Si le script apparaît aussi sur une installation propre du même thème et des mêmes plugins.
La décision “c’est légitime” doit être justifiée, sinon vous risquez de nettoyer en supprimant un composant qui était nécessaire, puis de garder l’infection ailleurs.
Étape de mitigation en attendant la suppression
Pendant que vous identifiez la source, vous avez deux objectifs, réduire le risque et conserver des preuves.
Si vous coupez trop tôt, vous risquez de ne plus savoir d’où ça venait. Si vous laissez tout en ligne trop longtemps, les visiteurs subissent.
Je recommande une approche pragmatique:
- Mettre le site en maintenance si l’effet est visible (redirections, pop-ups, dégradation nette). Désactiver temporairement des plugins non essentiels, mais avec prudence, car le comportement pourrait changer et rendre la source moins évidente. Bloquer les scripts externes au niveau serveur ou via une règle de filtrage uniquement si vous pouvez le faire sans casser l’interface. L’objectif est de contenir sans casser l’essentiel.
Dans certains environnements, une désactivation contrôlée d’un plugin suspect peut suffire à faire disparaître le chargement du script externe, ce qui confirme la piste. Mais ce n’est pas une garantie, car parfois le script est injecté via une combinaison de hooks et de templates.
Ce que je fais concrètement quand le script externe est identifié
Une fois que vous avez le domaine suspect et que vous voyez qu’il se charge systématiquement sur une page donnée, j’applique une séquence de correction orientée “origine”.
Première vague: neutraliser le chargement pour vérifier l’hypothèse
L’idée est de valider que le script externe est bien responsable du symptôme. On peut le faire de manière temporaire.

Au lieu de supprimer tout, je cherche à:
- supprimer ou neutraliser la balise côté serveur si elle est injectée en dur dans un template, ou désactiver le plugin responsable si l’initiator pointe vers lui.
Ensuite, je recharge et je vérifie si la requête disparaît.
Deuxième vague: corriger la cause, pas l’effet
Une fois validé, il faut revenir à la source, supprimer l’injection, puis remettre l’intégrité des fichiers.
C’est le moment où je fais:
- remplacement des fichiers de thème et de plugins par ceux d’origine (versions connues), suppression du code malveillant identifié, et nettoyage de données si une injection passe par la base.
Le remplacement d’origine a un avantage: il élimine les modifications subtiles. Le risque, c’est de perdre des personnalisations légitimes. Dans un site WordPress, il y a rarement zéro personnalisation. Il faut donc décider selon la réalité du projet: une customisation mineure peut être réappliquée plus tard, une configuration critique doit être conservée.
Checklist rapide: vérifier les scripts externes suspects
Voici ma mini-checklist, celle qui me fait gagner du temps sans tomber dans le théâtre.
- Repérer le domaine et le chemin exact de la requête script (pas seulement “un domaine” approximatif). Confirmer le déclenchement, sur plusieurs rechargements, page identique, moi connecté et non connecté si pertinent. Vérifier l’initiateur dans l’onglet Réseau, pour savoir si c’est un script inline, un fichier thème, ou un plugin. Comparer avec une page “saine” ou avec un environnement connu si vous en avez un. Conserver une capture de la source HTML et des requêtes Réseau avant modification, pour revenir en arrière.
Mettre à l’épreuve les hypothèses: tests utiles et pièges
Un incident peut être trompeur. Il arrive que le script externe ne soit pas l’origine, mais un relais. En d’autres termes, le vrai malware charge un premier script, puis celui-ci charge une seconde charge utile. Vous voyez la première requête et vous pensez avoir trouvé le coupable, alors que la modification est plus profonde.
Un autre piège: les scripts peuvent être chargés uniquement si certaines conditions sont remplies. Par exemple, si l’utilisateur a un cookie spécifique, ou si la page correspond à un motif d’URL, ou si un paramètre GET est présent. Si vous testez une seule fois, vous pouvez conclure trop vite.
C’est pourquoi je teste au moins deux variantes de contexte quand c’est possible. Le plus rentable est souvent:
- navigateur “propre” (profil sans cookies, ou incognito), navigateur “récurrent” (cookies présents), et parfois un compte admin et un compte visiteur.
Si le script ne se charge que dans un contexte, la source et la condition d’injection deviennent plus lisibles.
Durcir WordPress après le nettoyage, sans se tirer une balle dans le pied
Une fois le nettoyage fait, le vrai travail consiste à éviter la récidive. Vérifier les scripts externes suspects sert aussi d’indicateur, car c’est souvent le symptôme qui revient si une faille reste ouverte.
Le durcissement n’est pas qu’une question de “sécurité maximale”. C’est un équilibre entre réduction de surface, maintenance réaliste et compatibilité des plugins.
Par exemple, renforcer les politiques de contenu comme la csp peut être efficace, mais si votre site charge des scripts depuis de nombreux partenaires, vous allez devoir gérer une liste blanche. Sinon, vous cassez des fonctionnalités sans rapport direct avec l’infection.

Je préfère donc une approche progressive:
- rétablir des plugins et thèmes à des versions cohérentes, retirer ou désactiver ceux qui n’ont pas d’utilité, et mettre en place un suivi de la présence de domaines inattendus.
Un repère simple pour surveiller sans tout casser
Plutôt que de viser un mode “parano total”, je garde l’œil sur les domaines externes réellement chargés sur les pages publiques. Quand un domaine apparaît d’un coup, c’est un signal.
Et si vous avez des outils de monitoring, alertez sur:
- les nouveaux domaines appelés sur vos pages clés, les changements de code dans vos templates sensibles, les tentatives d’accès répétées aux zones d’administration.
Voici la deuxième checklist, courte, orientée prévention.
- Mettre à jour WordPress, thèmes et plugins (en privilégiant ce qui est utilisé). Retirer les plugins obsolètes ou ceux dont vous ne pouvez pas expliquer l’usage. Vérifier que les fichiers PHP sensibles n’ont pas de modifications inhabituelles. Surveiller les nouveaux scripts externes sur les pages publiques. Mettre en place une sauvegarde régulière, testée en restauration au moins une fois.
Quand faire appel à un diagnostic plus poussé
Je garde ce point pour les cas où la simple vérification des scripts externes ne suffit pas, ou quand elle révèle des signaux trop ambigus.
Si vous observez:
- des redirections impossibles à reproduire de façon fiable, des injections qui changent d’un test à l’autre, des scripts qui semblent tirer des charges utiles multiples dans une chaîne, une difficulté à attribuer l’initiation à un fichier thème ou plugin,
Alors il faut envisager un niveau d’investigation plus profond, parfois avec une analyse de cohérence des fichiers, une revue des accès, ou un examen de la base.
Dans certains hébergements, l’infection peut aussi toucher des niveaux non standards. Sans entrer dans des suppositions, le principe est que la méthode “scripts externes” reste un excellent déclencheur, mais pas toujours une preuve suffisante.
Exemple de scénario réel, typique, et comment la piste “script externe” a mené au bon endroit
Sur un site vitrine, le symptôme était une légère surchauffe de la page d’accueil, puis des publicités qui apparaissaient sur mobile. Dans WordPress, rien d’évident: pas de plugin de publicité installé, pas de modification visible du thème.
Le diagnostic a commencé comme prévu, avec l’onglet Réseau. Une requête vers un domaine inconnu apparaissait uniquement sur mobile. L’initiateur pointait vers un script inline dans la page, mais pas dans la zone qu’on attend d’habitude, plutôt au milieu du footer.
Ensuite, en regardant la source HTML, on a retrouvé la balise injectée, avec un fragment encodé. En cherchant ce fragment dans le thème et le dossier plugins, un fichier de thème avait une modification minuscule: un hook qui ajoutait une balise selon des conditions liées à la redimension mobile.
Le script externe n’était pas “toute l’infection”, mais c’était clairement le levier. Une fois le code retiré, la requête a disparu, et les publicités aussi. Le nettoyage a ensuite consisté à remplacer le thème par une version propre et à auditer les plugins récemment mis à jour.
Ce type de chemin est fréquent: vous voyez le symptôme côté navigateur, et la vérification des scripts externes vous ramène à la source PHP ou à la donnée injectée.
Rester méthodique, surtout quand on est sous pression
Le plus dangereux dans un incident, ce n’est pas seulement le malware, c’est la précipitation. On a envie d’effacer vite, de “rester en ligne”, de couper ce qui semble suspect. Or, sans traçabilité minimale, vous risquez de:
- supprimer le symptôme sans corriger l’origine, garder une porte ouverte, ou rendre le site instable après un nettoyage incomplet.
La vérification du chargement de scripts externes suspects est une approche efficace parce qu’elle se base sur des preuves observables, côté navigateur, et qu’elle se relie ensuite à l’origine côté serveur.
Si vous ne faites qu’une chose pendant le diagnostic, faites celle-ci: identifiez un script externe concret, notez-le, puis remontez l’initiateur. C’est souvent le fil qui permet de sortir du brouillard, avant même d’ouvrir dix fichiers dans tous les sens.
Si vous voulez, dites-moi votre contexte (type de site, extensions utilisées, symptôme observé, et si vous avez accès à une page de staging). Je pourrai vous proposer une stratégie d’investigation adaptée, toujours centrée sur le chargement des scripts et la remontée à la cause.