WordPress sait faire simple côté usage, mais côté exposition réseau il peut devenir pénible si l’on garde une configuration “par défaut”. Un site a de quoi attirer des scanners, des bots opportunistes, des tentatives de brute force et, plus sournoisement, des requêtes qui cherchent des angles morts dans le serveur HTTP.
Quand je parle de hardening WordPress, je pense rarement à un seul réglage magique. C’est plutôt un empilement de petites décisions, faciles à vérifier, qui réduisent la surface d’attaque. Sur Nginx, deux leviers reviennent presque toujours : limiter les méthodes HTTP acceptées et désactiver la liste de répertoires. Deux actions simples, mais qui bloquent déjà beaucoup de bruit inutile et certaines branches d’attaque.
Pourquoi viser d’abord Nginx
Avant d’écrire des règles partout, je préfère m’assurer que la “porte d’entrée” fait le tri. Nginx se place devant PHP-FPM, devant WordPress, et peut refuser des requêtes avant qu’elles ne déclenchent un traitement lourd côté application.

Dans la pratique, les mauvaises requêtes ont tendance à venir de :
- formulaires automatisés, qui tentent POST et GET en boucle, scanners qui testent des méthodes inhabituelles comme PUT, DELETE, TRACE, tentatives de lecture de contenu par exploration de chemins (le fameux “directory listing” quand il est accidentellement activé).
Le hardening Nginx ne remplace pas le durcissement WordPress, mais il rend l’ensemble plus robuste. Et il est souvent plus facile de le valider avec des tests simples.
Désactiver la liste de répertoires, même si vous croyez l’avoir fait
La liste de répertoires, c’est le cas où un visiteur tombe sur un URL de dossier, et voit une page qui affiche le contenu du dossier. Sur WordPress, on ne veut pas que le serveur rende ce type d’information. Même si, dans une configuration “normale”, WordPress sert surtout des fichiers, une mauvaise directive peut exposer des chemins inattendus.
Sur Nginx, cela se joue principalement avec autoindex. Par défaut, selon la distribution et la version, ce n’est pas toujours activé, mais je ne pars jamais de ce postulat en environnement réel.
Voici le type de réglage que j’utilise pour un site WordPress, dans le bloc server (ou dans le location pertinent, l’essentiel est que autoindex soit clairement désactivé pour les zones servies) :
Server Server_name example.com; Root /var/www/example.com; Autoindex off; Location / Try_files $uri $uri/ /index.php?$args;Deux points d’attention que j’ai appris à la dure :
Si vous avez plusieurs blocs server (HTTP, HTTPS, variantes, vhosts), il faut vérifier que la règle autoindex off; ne s’applique pas seulement à un des blocs. Si vous utilisez des fichiers “include” (par exemple include /etc/nginx/conf.d/*.conf;), un autre fichier peut réintroduire une configuration plus permissive. En cas de doute, faites une recherche dans /etc/nginx/ pour autoindex et examinez l’ensemble.Pour vérifier concrètement, je tente un URL de type “dossier” qui n’existe pas forcément. Par exemple, si votre root est /var/www/example.com, je regarde comment Nginx se comporte sur un chemin comme /wp-content/uploads/ selon la réalité du disque. L’objectif n’est pas de “tester la présence d’un fichier”, mais de vérifier que Nginx refuse de produire une page d’indexation.
Limiter les méthodes HTTP : réduire la surface d’attaque
Sur beaucoup d’installations, Nginx laisse passer large par défaut, puis WordPress rejette ce qu’il ne comprend pas. Ce n’est pas toujours une bonne idée. D’abord parce que vous payez parfois un coût inutile (logs, traitement, passage vers PHP), ensuite parce que certaines méthodes peuvent ouvrir des comportements non voulus si la config est particulière.
Les méthodes utiles pour WordPress dépendent de votre usage, mais globalement :
- GET et HEAD servent à lire, POST sert aux formulaires (connexion, publications, commentaires, admin-ajax selon le cas), OPTIONS est parfois utile pour des comportements spécifiques (CORS, prévols, etc.), tout le reste n’est généralement pas nécessaire pour un site WordPress standard.
Plutôt que de “faire confiance” à l’application, Nginx peut rejeter directement les requêtes inadaptées.
Je fais généralement cela dans le bloc server, en m’appuyant sur une combinaison de règles lisibles. Nginx propose if et return, mais il faut rester prudent avec les pièges de syntaxe. Mon approche est de garder des règles simples, sans imbrication compliquée.
Voici une manière pragmatique de refuser les méthodes souvent testées par les scanners. L’idée est de rendre la configuration explicite, https://gardewp.fr/securite-wordpress/ et donc audit-able :
- - Méthodes à limiter (site WordPress standard) :
Je dis “à réserver” pour OPTIONS, parce que dans certaines intégrations front (CORS, fetch cross-origin, ou outils externes), vous pouvez en avoir besoin. Sur un WordPress “classique” qui sert une page web simple sans contraintes CORS particulières, vous pouvez souvent vous en passer, mais je préfère le valider plutôt que de casser sans savoir.
Pour intégrer les refus dans Nginx, un exemple de bloc dans server peut ressembler à ceci :
Server HEADJe choisis ici 444 parce que c’est une pratique répandue dans certains environnements Nginx: la connexion est fermée sans réponse, ce qui réduit la surface en termes de contenu renvoyé. Vous pouvez aussi utiliser 403 selon votre politique. Le point clé n’est pas la valeur exacte, c’est la décision de ne pas “laisser passer” sans raison.
À ce stade, je recommande de tester avec une méthode non autorisée depuis votre poste, par exemple en remplaçant la méthode HTTP. Si votre environnement de test renvoie du trafic dans des journaux, vous verrez immédiatement si la règle se déclenche. Un test simple peut suffire, par exemple avec curl en changeant la méthode. Vous ne cherchez pas un exploit, vous cherchez à confirmer le comportement attendu.
Le cas délicat : admin-ajax.php, REST API et limites trop agressives
Le piège, c’est quand on bloque trop large. WordPress utilise des endpoints qui dépendent du front, plugins, ou intégrations.
- L’API REST de WordPress passe souvent par GET, POST, parfois PUT ou DELETE selon l’usage et les droits. Certains plugins d’authentification ou de synchronisation peuvent utiliser d’autres méthodes. Des caches et outils externes peuvent aussi varier.
Dans un hardening WordPress sérieux, on ne vise pas “la théorie parfaite”, on vise une configuration qui correspond à votre site, vos plugins, et vos flux.
Concrètement, si vous avez une application externe qui consomme l’API WordPress (par exemple, un front mobile qui fait du CRUD), vous aurez peut-être besoin de PUT ou DELETE au niveau de l’API. Dans ce cas, vous pouvez appliquer une politique par zone.
Par exemple, vous pouvez autoriser certaines méthodes uniquement vers l’endpoint REST, et refuser le reste. Cela demande de connaître vos usages. Nginx peut différencier avec des location, mais attention à ne pas créer une usine à gaz. Le bon sens consiste à commencer simple (limiter l’ensemble), puis assouplir uniquement là où c’est nécessaire.
Je le formule comme une règle de travail : d’abord, réduire ce qui est inutile. Ensuite, documenter chaque exception introduite pour un besoin réel.
Une règle qui protège sans casser : try_files, suppression des interprétations inattendues
La façon dont Nginx route vers WordPress compte autant que les méthodes. Dans une conf classique, on utilise try_files $uri $uri/ /index.php?$args; dans location /. Cela évite que Nginx serve des fichiers “fantômes” ou qu’il se trompe de traitement.
Cette ligne n’est pas un bouclier contre tout, mais elle réduit des comportements bizarres. Elle limite aussi certaines requêtes qui tentent d’accéder à des chemins non attendus, car Nginx renvoie à WordPress plutôt que d’exposer un comportement de fichier statique incohérent.
Un point que je surveille aussi : la manière dont location et root sont définis. Si vous avez des location spécifiques (par exemple pour /wp-admin ou /wp-content), vérifiez qu’ils ne contiennent pas des directives contradictoires du type autoindex on; ou des redirections inattendues.
Logging et “réponse noire” : choisir entre visibilité et discrétion
Quand on bloque des méthodes, on doit décider ce que vous voulez voir dans les logs.
- Si vous utilisez return 444;, vous réduisez la réponse HTTP renvoyée et vous rendez la fuite d’information plus faible. Si vous utilisez return 403;, vous aurez un état clair et vous pourrez corréler facilement avec vos règles.
Sur des environnements où le monitoring est strict, 403 facilite certains dashboards. Sur des environnements où vous cherchez surtout à fatiguer le moins possible des bots, 444 est plus silencieux.
Dans les deux cas, je pense “gestion opérationnelle”. Si vos logs deviennent trop bruyants, vous finirez par les ignorer, et donc vous perdez une partie de la valeur du durcissement. La meilleure stratégie consiste à garder un niveau de logs qui permet d’observer un changement, pas d’engorger le système.
Validation : comment savoir si le durcissement ne vous gêne pas
Je fais toujours une validation en trois temps : comportement, compatibilité, et régression.
D’abord, je vérifie que le site “standard” fonctionne : pages publiques, médias, formulaires qui utilisent POST, et endpoints admin qui doivent répondre.
Ensuite, je passe sur la compatibilité des méthodes. Je teste une requête avec une méthode non attendue et je confirme qu’elle est refusée. Je fais pareil pour les méthodes utiles, notamment POST.
Enfin, je m’assure que les plugins critiques ne sont pas cassés. Un plugin peut faire un appel atypique, et vous ne le verrez pas immédiatement si vous n’utilisez pas la fonction correspondante tous les jours. C’est pour ça que je garde une courte routine de tests avant chaque déploiement.


Contrôles rapides que je fais après modification Nginx
- Vérifier la présence de autoindex off; dans tous les vhosts pertinents, pas seulement un bloc. Vérifier que la règle de méthodes ne bloque pas des endpoints utilisés par votre front ou vos plugins. Tester un chemin “dossier” non routable pour confirmer l’absence de liste de répertoires. Regarder les erreurs Nginx après redémarrage, sinon on peut deviner trop tard qu’un include a fait diverger la config.
Config Nginx complète : un exemple cohérent, sans surcomplication
Voici un exemple de structure de server qui regroupe les deux objectifs, limiter les méthodes et désactiver la liste. Je le montre pour donner une cohérence, à adapter à votre environnement (certificats, headers, PHP-FPM, etc.) :
Server jpegDeux remarques sur cet exemple :
- Le bloc location ~ \.php$ et le passage à PHP-FPM ne sont pas la cible principale de votre question, mais ils montrent que la logique de routage n’empêche pas l’exécution de PHP là où il faut. La règle de méthode est globale dans ce server. Si vous avez des besoins particuliers sur l’API REST ou un plugin qui utilise d’autres méthodes, il faudra affiner avec des location ciblés.
Cas réels qui m’ont fait ajuster la règle “GET|HEAD|POST”
Sur un projet, nous avions un front qui consommait l’API REST avec certains appels qui utilisaient PUT. Après durcissement, ces appels ont échoué, et la fonctionnalité n’était pas visible au premier coup d’œil. La correction a consisté à :
- conserver la limitation globale, ajouter une exception uniquement sur l’endpoint concerné, documenter l’exception pour éviter qu’elle devienne un “chemin de contournement” non maîtrisé.
Dans un autre cas, un plugin de sauvegarde ou une intégration webhook émis par un système externe a demandé une méthode différente. Rien de dramatique, mais ce genre de surprise confirme une vérité pratique : un hardening utile doit être vérifié avec votre écosystème, pas avec une liste théorique d’actions.
Ce que ces deux réglages n’empêchent pas (et c’est important)
Limiter les méthodes et désactiver la liste de répertoires améliorent la situation, mais ne résolvent pas toutes les problématiques.
- Une injection ou une escalade applicative reste possible si WordPress, les plugins, ou le thème sont vulnérables. Un attaquant peut toujours faire des requêtes GET ou POST malveillantes, et WordPress devra filtrer correctement. Les tentatives de brute force sur /wp-login.php nécessitent d’autres protections (auth rate limiting, restrictions réseau, gestion des sessions, etc.).
En durcissement WordPress, je vois ces actions comme une barrière supplémentaire qui coupe du bruit et empêche certaines catégories d’essais.
Si vous voulez aller plus loin sans tomber dans l’excès
Une fois que le site ne casse pas avec la limitation de méthodes et que la liste est bien désactivée, vous pouvez élargir avec des contrôles plus “défensifs” côté Nginx, comme des restrictions d’accès à certains chemins, des headers durcis, et une configuration qui évite d’exposer des fichiers sensibles.
Mais je garde une approche progressive. Le risque, sinon, c’est de produire une configuration qui marche “chez vous”, puis qui casse en production sous charge ou avec un plugin plus tard.
Commencer par autoindex off et une politique de méthodes claire, c’est un bon compromis, car c’est à la fois simple, efficace, et assez facile à expliquer pendant un audit.
Résumé actionnable
Si vous ne retenez que deux choses, gardez-les nettes :
La première : désactivez la liste de répertoires dans Nginx avec autoindex off; dans les bons blocs server ou location.
La seconde : limitez les méthodes HTTP au minimum utile à votre WordPress. Pour un site standard, GET, HEAD, POST couvrent généralement le gros du besoin. Les exceptions se font au cas par cas, par endpoint, parce que certains plugins ou intégrations utilisent d’autres méthodes.
C’est ce mélange de rigueur et de pragmatisme qui fait un hardening WordPress crédible, pas seulement théorique.