Supprimer malware WordPress : éliminer le spam injecté dans les pages

Quand un site WordPress se met à “parler tout seul”, ce n’est jamais vraiment drôle. Un jour tout marche, le lendemain vous trouvez des mots-clés sans rapport, des liens vers des sites douteux, ou carrément des blocs entiers de contenu ajoutés dans certaines pages. Le pire, c’est que ça peut être discret: la page a l’air normale pour les visiteurs, mais un clic au mauvais endroit montre une injection de texte, une redirection, ou des liens cachés.

Dans ce billet, je vais m’attarder sur un scénario très fréquent: le spam injecté dans les pages, souvent via un malware ou un plugin compromis. L’objectif n’est pas seulement de “faire disparaître ce que vous voyez”, mais d’éradiquer la cause, limiter la rechute et sécuriser le site pour éviter un retour rapide du problème.

Le symptôme: des pages qui se déforment, des liens qui n’y étaient pas

Le spam injecté a des signatures assez typiques. Parfois c’est une phrase qui n’a aucun sens dans la page, parfois un bloc de liens répétés en bas de page. Dans d’autres cas, c’est une modification plus subtile: vous voyez des ancres, des mots-clés longs, ou des sections entières qui apparaissent uniquement pour certains navigateurs ou certains pays.

Sur un site que j’ai accompagné, l’utilisateur pensait d’abord à un thème “qui bug”. En réalité, les injections avaient la même structure partout, mais variaient selon l’URL. Les zones touchées étaient liées à des hooks WordPress et à des templates chargés après l’affichage du contenu principal. Autrement dit, ce n’était pas juste un texte ajouté au hasard: il y avait une logique côté serveur, et probablement un fichier PHP modifié, ou un contenu inséré via une base de données.

Ce détail compte, parce qu’une injection peut avoir plusieurs chemins d’exécution:

    modification d’un fichier (thème, plugin, mu-plugin, ou un fichier “cache” exploité), ajout d’un code dans la base de données (options, post meta, champs cachés), compromission d’un compte (auteur, éditeur) qui publie ou retouche des pages, scripts qui changent le rendu en condition (utilisateur, agent, chargeur, langue).

Comprendre “où” et “comment” ça s’insère permet d’éviter un nettoyage superficiel qui ne fait que retarder le retour.

Première étape utile: identifier la zone exacte touchée

Avant de supprimer quoi que ce soit, je commence toujours par cartographier l’atteinte. L’idée est simple: si vous savez exactement quelles pages sont infectées, vous réduisez le champ de recherche et vous pouvez tester chaque correction.

Concrètement, vous pouvez comparer:

    une page infectée et une page saine sur le même modèle (même template), la version affichée avec un navigateur “normal” et un agent différent (pour voir si c’est conditionnel), le HTML reçu (via “afficher le code source” ou un inspecteur), pour repérer l’endroit où le texte ajouté s’insère.

Souvent, l’injection apparaît dans une portion générée côté serveur. Si vous voyez du spam au niveau du HTML final, c’est probablement du contenu inséré lors du rendu, pas seulement via un script client après coup. À l’inverse, si vous ne voyez rien dans le code source, mais que la page “bouge” en affichage, on peut avoir un script côté navigateur injecté, ou une ressource chargée dynamiquement.

C’est là que l’expertise opérationnelle devient importante: deux sites peuvent afficher “du spam dans les pages”, mais les causes internes peuvent être radicalement différentes.

Ne tombez pas dans le piège du “plugin qui a tout cassé”

WordPress est un écosystème vivant, il y a beaucoup de plugins, et certains font des choses “un peu limites” sans que ce soit malveillant. Le risque, c’est de supprimer un plugin au hasard et de rater la vraie porte d’entrée.

J’ai vu des nettoyages où l’équipe supprimait un plugin suspect, puis constatait que le spam revenait. La cause n’était pas le plugin principal, mais une modification ailleurs: un fichier dans un répertoire inattendu, une tâche planifiée, ou un compte utilisateur compromis qui réinstallait ou resémoquait le code.

Donc, oui, il faut suspecter les plugins et thèmes, mais il faut aussi vérifier ce qui a été modifié récemment et ce qui déclenche l’injection.

Vérifications rapides côté administration (sans casser la piste)

Avant de toucher aux fichiers, regardez ce que l’administration peut encore vous dire.

    Vérifiez la liste des utilisateurs et repérez les comptes récents, les rôles inhabituels, ou des identifiants qui n’ont aucun contexte. Regardez l’historique d’activité si vous en avez (selon la configuration, journaux, plugins de sécurité, ou logs d’hébergement). Contrôlez les médias ajoutés récemment, les pages et brouillons créés, parfois même des révisions.

Si un compte a été compromis, il peut aussi servir à réinjecter le spam en arrière-plan. Dans ce cas, supprimer les fichiers ne suffira pas, tant que l’accès n’est pas neutralisé.

Vérifier les fichiers: le vrai cœur du problème

Le spam injecté dans les pages repose souvent sur une modification de code côté serveur. En pratique, on retrouve fréquemment:

    un fichier PHP dans un thème ou un plugin modifié, un petit bout de code dissimulé dans un fichier “innocent” (par exemple en fin de fichier), des fichiers supplémentaires ajoutés dans des dossiers bizarres (noms courts, répertoires non utilisés), des mécanismes qui s’activent uniquement quand certaines conditions sont remplies (langue, type d’utilisateur, page demandée).

La méthode que je privilégie est pragmatique: comparer l’état actuel avec une version saine (quand c’est possible), ou au minimum rechercher les modifications récentes et les ajouts de patterns typiques (base64, eval, preg_replace avec une logique étrange, fonctions d’écriture disque, etc.).

Si vous utilisez un hébergement qui vous permet d’accéder facilement aux journaux, reliez les dates: si l’injection apparaît “à l’heure près” d’une connexion, cela donne une piste.

En cas de doute sur un fichier précis, je conseille de ne pas “bricoler” directement. Soit vous supprimez et remettez le fichier à l’identique d’une source fiable, soit vous restaurez un backup connu.

Vérifier la base de données: options, métadonnées et contenus cachés

Le spam peut être injecté via la base de données, et c’est plus fréquent qu’on ne le pense. Par exemple:

    des options modifiées (scripts, templates, codes d’affichage), des champs méta attachés à des posts qui sont ensuite rendus, des scripts stockés dans des zones de configuration, des “shortcodes” créés par un acteur malveillant.

Le point important: supprimer un plugin ou restaurer un thème ne garantit pas une neutralisation si le code malveillant est stocké côté base. Inversement, nettoyer la base sans corriger le point d’entrée, c’est ouvrir la porte aux réinfections.

Si vous avez des sauvegardes, l’approche la plus fiable consiste à:

1) restaurer la base depuis avant l’incident, 2) restaurer les fichiers depuis avant l’incident, 3) corriger la faille d’accès, 4) remettre le site en ligne avec une surveillance renforcée.

Si vous n’avez pas de sauvegarde exploitable, la tâche devient plus délicate, mais elle reste possible en analysant la base à la recherche de valeurs suspectes et en comparant avec des exports propres.

Le moment où tout bascule: isoler le point d’entrée

Pour supprimer malware WordPress de manière durable, il faut traiter la cause, pas seulement la conséquence visuelle.

Le point d’entrée le plus courant reste la compromission d’un compte WordPress (mot de passe réutilisé, brute force, absence de 2FA, plugin de gestion de mots de passe, ou faille d’un plugin exposé). Plus rarement, c’est une faille d’un plugin ou d’un thème non maintenu qui permet d’exécuter du code.

Il existe aussi des cas où le serveur ou le compte FTP est vulnérable, et où l’attaquant dépose des fichiers directement, sans passer par WordPress.

C’est pour cela que, dans un incident réel, je fais un audit “petit mais complet”:

    comptes WordPress: suppression des comptes inconnus et réinitialisation des mots de passe, fichiers: repérage des modifications récentes et restauration des composants, scheduled tasks: vérification des tâches planifiées si elles sont liées à des plugins, accès hébergement: vérification des connexions et des clés.

Procédure de nettoyage recommandée (sans se tirer une balle dans le pied)

Je vais maintenant décrire une procédure réaliste. Elle ne remplace pas une expertise complète, mais elle suit une logique qui évite le faux sentiment de sécurité.

1) Mettre le site hors ligne ou en mode maintenance

Même si ça gêne un peu, ça protège vos visiteurs et ça stoppe le cycle “injection puis indexation”. Si vous avez un trafic important, vous pouvez limiter au maximum l’exposition, mais dans tous les cas, gardez un minimum de contrôle.

2) Sauvegarder avant toute action

Sauvegarder n’est pas un formalité. Si vous devez revenir en arrière, c’est votre filet de sécurité. Faites au moins une archive des fichiers WordPress et un export de la base.

3) Identifier le périmètre: thème, plugins, mu-plugins, uploads

Pour un site touché par du spam injecté dans des pages, je commence par:

    restaurer le thème depuis sa source fiable (ou supprimer le thème modifié et reprendre une version saine), désactiver puis supprimer les plugins non essentiels, contrôler spécifiquement le contenu dans wp-content/plugins et wp-content/mu-plugins, inspecter wp-content/uploads (les images sont rarement en cause, mais les scripts déposés peuvent s’y cacher selon la configuration d’exécution).

4) Restaurer proprement ce qui a des chances d’être modifié

Dans la pratique, les restaurations “au bon endroit” font gagner un temps énorme. Sur WordPress, quand un thème ou un plugin est compromis, la restauration depuis une version saine évite de devoir reconstruire manuellement le fichier.

Je ne suis pas fan de “j’enlève juste les lignes suspectes” quand la quantité de modifications est inconnue. Le risque, c’est de laisser un morceau actif ailleurs.

image

5) Couper la réinfection côté comptes

Si vous constatez des https://gardewp.fr/nettoyage-malware-wordpress/ comptes suspects, supprimez-les. Si vous n’êtes pas sûr, changez tous les mots de passe (au minimum admin, éditeurs, et comptes techniques). Et si vous avez la main sur l’hébergement, changez aussi les identifiants FTP, SSH, et clés.

Ajoutez ensuite 2FA si vous pouvez, et activez une limitation contre les tentatives d’accès.

6) Nettoyer la base quand l’injection est stockée

Si le spam vient d’options ou de métadonnées, il faut nettoyer les valeurs corrompues. Sans entrer dans des réglages trop risqués, l’approche sûre consiste à restaurer la base depuis un point antérieur à l’incident, puis à appliquer uniquement les mises à jour nécessaires.

7) Réactiver en mode contrôlé, puis surveiller

Ne remettez pas tout d’un coup. Remettez d’abord WordPress avec uniquement le nécessaire (thème propre, plugins indispensables), puis réintroduisez les plugins un par un en surveillant les pages. Ça vous permet de repérer immédiatement quel composant déclenche à nouveau l’injection.

Comment repérer un code injecté “à la main” (sans être développeur)

Vous n’avez pas besoin d’être expert en sécurité pour repérer des signaux.

Ce que je cherche, c’est la présence de patterns incohérents dans des fichiers qui n’ont aucune raison d’en contenir. Par exemple, une page de thème qui charge une logique de génération de liens ne devrait pas soudainement contenir un bloc de code qui:

    déchiffre une chaîne base64 puis exécute le résultat, utilise eval ou assert, fait des requêtes sortantes vers des domaines sans rapport avec le site, écrit dans le système de fichiers, modifie la réponse en fonction de critères cachés.

La difficulté, c’est que le malware peut se déguiser, mais il laisse souvent une trace.

Astuce opérationnelle: faites-vous une liste de pages atteintes, puis après chaque correction, testez ces pages et vérifiez le code source HTML. Si le spam disparaît, le dernier changement est probablement utile. Si le spam revient, c’est que le point d’entrée n’est pas neutralisé.

Un exemple concret de traitement d’un “pattern d’injection” dans WordPress

Sur un autre site, le spam apparaissait sur un sous-ensemble de pages: uniquement des pages créées avec un constructeur de contenu, et uniquement pour certaines requêtes. En inspectant, on a vu que le bloc ajouté ne venait pas du contenu du post en lui-même. Il était injecté au moment du rendu, via un hook qui s’exécutait après le contenu.

image

Le nettoyage a suivi une stratégie en trois temps:

1) désactivation des plugins non essentiels pour confirmer la dépendance, 2) restauration du thème pour éliminer les modifications dans le template, 3) recherche dans la base sur des options liées aux comportements d’affichage.

Le détail qui a fait gagner le plus de temps: le code injecté était présent même après désactivation de plusieurs plugins, preuve que la source se situait ailleurs que dans la fonction du plugin principal. Finalement, la base contenait une valeur de configuration “cassée” utilisée par un mécanisme de rendu. Une restauration de la base à un point antérieur a réglé l’effet visible, mais pas complètement. Il a fallu ensuite neutraliser le compte https://gardewp.fr/ qui avait réinjecté la configuration.

Morale de terrain: on traite les deux couches, code et accès.

La prévention réaliste après suppression malware WordPress

Quand le site redevient propre, l’envie est forte de repartir comme avant. C’est exactement là que les infections reviennent.

La prévention, ce n’est pas “mettre un scanner magique”. C’est réduire la surface d’attaque et améliorer la détection.

Après un incident, je recommande de:

    limiter l’accès aux comptes WordPress, supprimer les rôles inutiles, activer 2FA pour les comptes admin, mettre à jour WordPress, thèmes et plugins dès que c’est viable, supprimer ou remplacer les plugins qui ne sont pas essentiels, contrôler les permissions sur les répertoires sensibles, installer une protection anti-bots et surveiller les logs d’accès, maintenir des sauvegardes régulières, testées au moins une fois pour vérifier la restauration.

Si vous ne faites pas ces points, vous pouvez avoir un site “net” pendant une semaine, puis une rechute au même endroit.

Mini check de diagnostic (utile quand vous hésitez sur la cause)

Voici une liste courte, basée sur ce que je vois le plus souvent. Elle aide à trier rapidement l’hypothèse la plus probable:

    Le spam disparaît après désactivation d’un plugin spécifique: attention à une injection via plugin compromis ou à un hook malveillant. Le spam reste malgré la désactivation de plugins: suspectez thème, mu-plugins, ou base de données. Des comptes ont été créés récemment: suspect prioritaire, car la réinfection est probable. Le spam varie selon l’agent ou le type de visiteur: malware qui conditionne son injection, souvent via du code PHP. Des fichiers ont été modifiés sans lien avec une mise à jour: piste de porte d’entrée via accès serveur ou upload.

Quand il faut passer la main à un spécialiste

Je suis prudent ici: chaque contexte a ses contraintes. Mais il y a des situations où continuer “à tâtons” coûte plus cher que de demander un audit.

Typiquement, je conseille d’envisager une aide externe si:

    vous n’avez pas de sauvegarde antérieure et vous ne savez pas ce qui a été modifié, l’injection est distribuée, multiple, et vous ne pouvez pas isoler la zone, vous voyez des signes d’accès serveur compromis (SSH, clés, scripts dans des répertoires inhabitués), vous recevez des notifications de blocage ou d’actions de sécurité qui indiquent des activités persistantes, le site a été utilisé pour distribuer des redirections ou du contenu malveillant ailleurs (cas plus grave).

Une intervention structurée évite souvent un cycle de “nettoyage puis rechute”.

Après remise en ligne: valider la propreté et surveiller les retours

Une fois le site réactivé, ne considérez pas l’incident clos tant que vous n’avez pas validé trois choses: pages propres, absence d’accès suspect, et absence de réinjection.

Le plus simple est de:

1) comparer les pages atteintes avant et après, 2) surveiller la création de contenus et les comptes, 3) garder un œil sur les logs d’accès serveur et WordPress.

Si vous avez accès à des outils de scan ou des rapports de sécurité côté navigateur, utilisez-les, mais avec du recul. Un scan peut signaler un faux positif, et à l’inverse un malware qui injecte de manière conditionnelle peut passer sous le radar. Le HTML réellement servi reste la meilleure preuve, et les logs restent votre meilleure chronologie.

Le piège final: se débarrasser du spam, pas de la faille

Supprimer malware WordPress, ce n’est pas uniquement “faire disparaître le texte injecté”. Le vrai succès, c’est quand vous empêchez la prochaine injection.

Dans beaucoup d’incidents, le spam est une conséquence visible, mais la faille est invisible. Quand on restaure uniquement les fichiers sans corriger la porte d’entrée, le site se nettoie bien, puis redevient sale. Quand on corrige la base sans corriger les accès, un compte compromis réécrit les valeurs et le spam revient.

C’est une double logique, code et accès. Les entreprises qui s’en sortent le mieux sont celles qui traitent les deux en même temps, avec une validation par test des pages et par surveillance.

Ressources internes que je garde toujours sous la main

Sans entrer dans une liste interminable (sinon on finit par ne rien faire), je garde surtout un principe: chaque incident doit laisser une trace utile.

Après résolution, je note:

    quelles pages étaient injectées, quelle technique d’injection était visible (code PHP au rendu, base, redirection), quel point d’entrée a été corrigé (compte, plugin, thème, accès serveur), quelles mesures de prévention ont été ajoutées, à partir de quelle date le site est fiable.

Ce “petit dossier” accélère la prochaine fois, même si la prochaine fois n’arrive jamais.

image

Si vous me décrivez votre cas avec trois informations, je peux vous aider à affiner le diagnostic et la stratégie de suppression: le type de spam visible (liens, texte, blocs entiers), la page ou le template touché, et si vous avez repéré des comptes récents ou des fichiers modifiés récemment.