Un JavaScript inconnu dans le pied de page : d'où il vient
Injection en base (options, widgets), thème modifié, ou plugin pirate. Un JavaScript inconnu dans le pied de page ne « vient pas de Google ». Comparez le HTML servi à un visiteur et celui de l’admin : ils diffèrent souvent. Le footer que vous éditez dans l’apparence n’est pas toujours le footer que le mobile télécharge.
Injection en base (options, widgets), thème modifié, ou plugin pirate. Comparez le HTML servi à un visiteur et celui de l'admin : ils diffèrent souvent.
Trois origines, pas une « erreur de thème »
Un JavaScript inconnu dans le pied de page : balise `<script src="https://…">` ou un pavé inline (`eval`, `atob`, un domaine que personne de l’équipe ne connaît). Trois tiroirs. A) La base WordPress / Presta (options, widgets, hooks CMS). B) Un fichier de thème (footer.php, un JS du builder). C) Un plugin, un must-use, un prepend qui echo avant `wp_footer`. Traiter un seul tiroir, c’est le scénario « on a remis footer.php, le script est encore là ».
Ce n’est pas Rank Math, Yoast, ou « le SEO » par nature. Un plugin SEO peut être le véhicule (option, champ HTML) ; la cause est une écriture non autorisée. Voir Rank Math / Yoast pas la cause si on vous vend ça comme diagnostic.
Mots-clés : javascript injecté WordPress, script inconnu footer, js malware site. Le footer est le lieu de confort des injections : chargé sur toutes les pages, rarement relu, mélangé aux vrais pixels.
- Noter l’URL exacte du script (host + path).
- HTML visiteur (privée / GSC) vs HTML admin.
- Les trois tiroirs, dans n’importe quel ordre, les trois.
Ce que le visiteur reçoit vs ce que l’admin voit
View-source en privée, curl, inspection Search Console : le footer réel. L’éditeur Apparence → Pied de page, lui, montre le widget légitime. Le script pirate est dans `theme_mods`, dans un `autoload`, dans un cache page anonyme, ou injecté par PHP seulement si `!is_user_logged_in()`. Vous éditez le bon écran, le mauvais HTML.
D’où l’ordre : capturer le HTML visiteur d’abord (captures du source, ou fichier `.html` sauvé). Puis chercher cette chaîne. Pas l’inverse (« je ne vois rien dans l’admin donc c’est bon »).
Mobile vs desktop : le builder sert parfois deux footers. Testez les deux. Mobile si le JS, en plus, redirige.
Piste A — les options et les widgets
phpMyAdmin, base du site, recherche du hostname du script ou de `eval(` / `atob(` dans `wp_options`, `wp_posts` (révisions aussi), tables Elementor. Les hits `widget_custom_html`, `widget_text`, `custom_css`, `scripts_in_footer`, `header_scripts` (plugins « insert headers and footers » — souvent le tiroir le plus simple à lire, et le plus oublié).
Un plugin « insert headers » légitime dont le champ a été rempli par l’attaquant : vous « n’avez pas de malware fichier ». Vous avez un champ. Videz le champ, pas tout le plugin d’abord (vous perdriez aussi votre vrai GTM — copiez les champs avant).
PrestaShop : `html` modules, `ps_customtext`, hooks footer. Magento : layout XML, CMS blocks. Même chasse, autres tables.
Piste B — le thème et les builders
`footer.php`, `functions.php` (`wp_enqueue` d’un host inconnu, ou `echo` dans `wp_footer`), un `custom.js` daté d’hier. Diff vs zip parent. Enfant : lecture. Elementor / WPBakery : CSS/JS custom du kit, templates. Un « HTML widget » collé sur toutes les pages via le theme builder : c’est encore le footer, ailleurs dans l’UI.
Les thèmes nulled arrivent déjà avec un JS. Changer de thème sans inspecter `mu-plugins` laisse le C. WordPress piraté : thème hors circuit.
Ne réinstallez pas le thème par-dessus sans copie : vous perdez l’enfant custom, pas forcément le script en base (A).
Piste C — un plugin (ou un mu-plugin) que vous n’avez pas posé
Dossier plugin à nom anodin (`wp-helper`, `seo-fix`, `cache-cdn`), mu-plugins (`index.php` d’une ligne), prepend `.user.ini` qui inclut un JS echo. Dates. Plugins désactivés : un mu-plugin ne se « désactive » pas dans l’UI. Listez `wp-content/mu-plugins` à chaque incident. Backdoor.
Un plugin de cache qui a figé le HTML sale : flush après retrait A/B/C, sinon le footer pirate vit dans `wp-content/cache`. Object cache : Redis.
GTM / Tag Manager : un tag HTML custom. Ce n’est ni A fichier ni B thème, c’est le compte Google. GTM. Pixel Facebook ajouté : même famille dashboard.
Comparer, extraire le host, grepper
Du HTML visiteur, copiez le `src` ou 20 caractères uniques de l’inline. Grep fichiers + SQL. Un seul host, parfois cinq scripts. Tous. Les encodeurs (`\x73\x63\x72\x69\x70\x74`) : cherchez `\x73` ou `fromCharCode` aussi, pas seulement `<script`.
Les commentaires `<!-- analytics -->` autour d’un faux pixel : lisez l’URL. Les attaquants aiment les commentaires rassurants.
Si grep zéro et GSC encore sale : cache, autre hostname (`www` vs apex), autre vhost. IPv6 / www.
Retirer sans casser Analytics et le chat
Listez vos scripts légitimes (GTM ID, Crisp, Hotjar que VOUS avez posé — attention Hotjar ajouté par l’attaquant). Retirez par host / par pavé encodé, pas « tous les script du footer ». Un empty `footer.php` = chat mort, tracking mort, parfois le layout.
Flush, privée, mobile, inspection. 48 h : le host a-t-il disparu du HTML ? `site:` ne montre pas toujours un JS ; GSC et curl si.
Ticket hébergeur si le JS est un kit connu (ils ont parfois le path). Constat : trouvé (option X / fichier Y), retiré, corrigé (entrée).
Filet : le script se réécrit à H+6
Cron, mu-plugin, admin encore là, Application Password, voisin. Le footer propre le soir, sale le matin : vous avez traité le symptôme. Checklist portes, secrets panel d’abord. Mots de passe.
Filet plugin sécu : après, alertes nouveau contenu / nouveau fichier. Pas comme cleaner. Wordfence pendant.
Un CSP `script-src` après coup aide à voir la prochaine (console navigateur). Testez GTM avant de figer. Ce n’est pas le nettoyage du jour J.