Table des matières de l'article :
Dans le monde de l'hébergement web, il existe une de ces « vérités » tellement répétée qu'elle est presque devenue un dogme : les répertoires doivent avoir des permissions. 755 et les fichiers doivent avoir les autorisations nécessaires 644Guides, tutoriels, panneaux de contrôle, fournisseurs généralistes, documentation d'assistance, forums et même certains outils de restauration automatique des permissions l'affirment. Le problème est que cette règle, bien que pratique et souvent efficace, n'est pas forcément la plus appropriée du point de vue de la sécurité.
L'objectif n'est pas d'affirmer qu'un site comportant 755 répertoires et 644 fichiers est automatiquement compromis ou totalement non sécurisé. Ce serait une simplification excessive, voire erronée d'une certaine manière. L'enjeu est différent : Les autorisations 755 et 644 sont conçues pour garantir une compatibilité universelle, et non pour respecter véritablement le principe du moindre privilège.Et c'est là que naît le malentendu, ou plutôt, le péché originel d'une grande partie de l'hébergement commercial basé sur des panneaux de contrôle comme cPanel, Plesk et autres.
Dans un système Linux multi-utilisateurs, le troisième chiffre des permissions, celui qui concerne les autres utilisateurs du système, ne doit pas servir de raccourci pour accéder au serveur web. Si ce dernier a besoin de lire les fichiers d'un site web, il doit pouvoir le faire soit parce qu'il appartient au groupe approprié, soit parce que le processus PHP s'exécute avec l'utilisateur adéquat, soit encore parce que l'architecture du service a été conçue de manière appropriée. Il ne s'agit pas de rendre le site web accessible à n'importe quel utilisateur local du système.
La véritable signification de 755 et 644
Commençons par les bases. Un permis 755 sur un répertoire signifie :
rwxr-xr-x
Le propriétaire peut lire, écrire et accéder au répertoire. Le groupe peut lire et accéder au répertoire. Tous les autres utilisateurs peuvent lire et accéder au répertoire. Sur un répertoire, le bit d'exécution ne signifie pas « lancer un programme », mais parcourir le répertoire, c'est-à-dire pouvoir y accéder, atteindre les fichiers et les sous-répertoires et résoudre le chemin d'accès.
Un permis 644 sur un fichier signifie :
rw-r--r--
Le propriétaire peut lire et écrire. Le groupe peut lire. Tous les autres utilisateurs peuvent lire. Ainsi, si un fichier PHP, un fichier de configuration ou un fichier texte a les permissions 644, tout utilisateur local qui n'est ni le propriétaire ni membre du groupe peut le lire, à condition d'avoir accès au répertoire parent.
Beaucoup pensent à tort qu'« il est impossible de lire le code source PHP via le web ». C'est vrai, si le serveur web est correctement configuré. Mais les permissions Linux régissent bien plus que le simple accès HTTP. Elles régissent également l'accès local depuis les shells, les processus système, les scripts compromis, les utilisateurs mal protégés, les tâches cron, les outils de sauvegarde, les comptes FTP ou SFTP, les autres sites hébergés sur la même machine, et tout processus s'exécutant sous un utilisateur local différent.
Dire que les permissions 755 et 644 sont « acceptables » revient souvent à ignorer le contexte multi-utilisateurs dans lequel ces permissions sont appliquées.
Pourquoi les panneaux utilisent-ils encore les fréquences 755 et 644 ?
La réponse est dérangeante mais simple : parce que ils fonctionnent presque toujoursLes panneaux de contrôle sont des produits généralistes. Ils doivent prendre en charge les anciennes et les nouvelles architectures, les serveurs bien et mal configurés, Apache avec mod_php, Apache avec PHP-FPM, Nginx comme proxy inverse, LiteSpeed, LSAPI, suPHP, suexec, FastCGI, les utilisateurs FTP, les gestionnaires de fichiers web, les sauvegardes, les restaurations, les migrations, les plugins WordPress, les installateurs automatisés, les anciens systèmes de gestion de contenu, les scripts mal écrits et les clients qui téléchargent des fichiers avec des permissions douteuses.
Dans ce scénario, 755 pour les répertoires et 644 pour les fichiers est le moyen le plus simple d'éviter les tickets de support. Si le processus web n'appartient pas au groupe approprié, si Apache s'exécute en tant que nobody, si Nginx fonctionne comme nginxSi le pool PHP-FPM n'est pas parfaitement aligné avec l'utilisateur du site, si le gestionnaire de fichiers a toujours besoin d'afficher et de manipuler des fichiers, ces autorisations garantissent une chose : le site restera probablement réactif.
Mais cela n'en fait pas pour autant les meilleurs permis. Cela simplifie la gestion des autorisations pour le fournisseur du panneau et pour l'opérateur souhaitant réduire les problèmes de compatibilité. C'est un changement majeur.
Lorsqu'un panneau attribue automatiquement les permissions 755 aux répertoires et 644 aux fichiers, il indique implicitement : « Je ne sais pas quel utilisateur ou groupe devrait lire ces fichiers, donc j'autorise les autres à les lire également. » C'est un choix pragmatique. Mais du point de vue du système, c'est un raccourci.
Le principe du moindre privilège
Le principe du moindre privilège stipule que chaque utilisateur, processus ou service ne doit disposer que des autorisations strictement nécessaires à l'exécution de sa fonction. Appliqué aux fichiers d'un site web, cela signifie :
- L'utilisateur propriétaire du site doit pouvoir lire et écrire les fichiers ;
- Le processus PHP doit pouvoir lire les fichiers PHP et éventuellement écrire uniquement dans les répertoires désignés ;
- Le serveur web doit pouvoir lire directement les ressources statiques dont il a besoin pour la diffusion ;
- Les autres utilisateurs du système ne devraient rien pouvoir lire ;
- Les fichiers sensibles ne doivent pas être lisibles par des processus non essentiels.
Si l'on prend ce principe au sérieux, la paire 755/644 apparaît immédiatement trop grande. La configuration la plus cohérente devient alors :
Directory: 750 File: 640
Ou encore, dans certains cas encore plus restrictifs :
Directory: 750 o 700 File: 640 o 600
Pour les fichiers particulièrement sensibles tels que wp-config.php, .env, configuration.php de Joomla ou app/etc/env.php Pour Magento, il peut être judicieux d'aller plus loin, selon la façon dont PHP accède au fichier.
WordPress, PHP-FPM et Nginx : pourquoi le modèle évolue
Une part importante de la confusion provient du fait que de nombreuses recommandations historiques sont issues d'environnements Apache traditionnels, souvent avec mod_php ou des configurations où le serveur web devait lire directement une grande partie du contenu. Dans le monde moderne, et notamment dans les environnements professionnels, un site WordPress ou PHP est souvent géré selon un modèle différent.:
- Nginx gère la connexion HTTP et sert les ressources statiques ;
- PHP-FPM exécute du code PHP ;
- chaque pool PHP-FPM peut s'exécuter en tant qu'utilisateur spécifique au site ;
- Le code PHP n'est pas « lu par Nginx » pour être interprété, mais transmis à PHP-FPM via FastCGI ;
- Les processus PHP peuvent être isolés par utilisateur, domaine ou abonnement.
Dans ce contexte, continuer à penser comme si tout devait être lisible par « d’autres » est techniquement rétrograde. Si PHP-FPM est exécuté avec les droits de l'utilisateur du site, les fichiers PHP sont accessibles en lecture par ce dernier. Si Nginx doit servir des fichiers statiques, il peut y accéder via le groupe. Il n'est donc pas nécessaire d'accorder l'autorisation de lecture au reste du réseau local.
Le modèle approprié consiste à concevoir la propriété et les groupes de manière cohérente. Par exemple :
owner: utente_sito group: web-utente_sito directory: 750 file: 640
Dans ce système, l'utilisateur du site conserve le contrôle des fichiers, tandis que le groupe accorde l'accès aux processus autorisés, tels que Nginx ou un service spécifique. Les autres utilisateurs n'y ont aucun accès.
Le problème de l'utilisation globale de nginx
Une solution apparemment simple pourrait consister à « placer Nginx dans le groupe de l'utilisateur » ou à « assigner les fichiers au groupe nginx ». Ce raisonnement est correct dans son intention, mais il doit être appliqué avec précaution.
Un exemple grossier pourrait être :
chown -R nomesito:nginx /home/nomesito/public_html
find /home/nomesito/public_html -type d -exec chmod 750 {} ;
find /home/nomesito/public_html -type f -exec chmod 640 {} ;
Cela fonctionne : Nginx, appartenant au groupe, peut parcourir les répertoires et lire les fichiers. Les autres utilisateurs ne peuvent rien faire. Cependant, si tous les sites du serveur utilisent le groupe global, nginxDans ce cas, tout processus exécuté sous le nom de Nginx peut potentiellement lire les fichiers de tous ces sites. Sur un serveur mono-site, cela peut être acceptable ; dans un environnement multi-utilisateurs, l’isolation est loin d’être optimale.
La solution la plus élégante consiste à utiliser des groupes dédiés par site ou par contexte d'application :
groupadd web-nomesito
usermod -aG web-nomesito nginx
usermod -aG web-nomesito nomesito
chown -R nomesito:web-nomesito /home/nomesito/public_html
find /home/nomesito/public_html -type d -exec chmod 750 {} ;
find /home/nomesito/public_html -type f -exec chmod 640 {} ;
Pour assurer la cohérence du groupe sur les nouveaux fichiers créés dans les répertoires, vous pouvez également utiliser le bit setgid sur les annuaires :
find /home/nomesito/public_html -type d -exec chmod g+s {} ;
Ainsi, les nouveaux fichiers créés dans ces répertoires héritent du groupe du répertoire parent. Ce n'est pas une solution miracle, car il faut toujours gérer les masques de création de fichiers (umask), les déploiements, le protocole SFTP, les processus PHP et les outils de mise à jour, mais c'est un modèle bien plus judicieux que de tout laisser à la portée de tous.
Pourquoi 750/640 est plus correct
Avec des répertoires à 750 et des fichiers à 640, on obtient une séparation beaucoup plus nette :
rwxr-x--- directory rw-r----- file
Le propriétaire a le contrôle total. Le groupe peut lire et accéder aux données. Les autres ne peuvent rien faire. Cela signifie qu'un autre utilisateur local ne peut pas fouiller dans les fichiers du site simplement parce que le panneau de contrôle a décidé d'utiliser des permissions permissives pour éviter les problèmes.
Sous WordPress, la différence est loin d'être anodine. Une installation WordPress peut contenir des fichiers de configuration, des identifiants de base de données, des clés d'authentification, des extensions personnalisées, des sauvegardes oubliées, des exportations, des journaux, des dumps SQL, des fichiers temporaires, des caches, des configurations de services externes, des jetons API, des identifiants SMTP, et bien plus encore. Bien sûr, nombre de ces fichiers ne devraient pas se trouver à la racine du site. Mais nous savons comment cela fonctionne dans la réalité : les sites accumulent des éléments, des extensions, des dossiers temporaires et des traces de migration.
Si toutes les données sont accessibles à d'autres, la moindre faille dans l'isolation locale peut entraîner une perte de confidentialité. Une vulnérabilité distante spectaculaire n'est pas forcément nécessaire. Parfois, un compte compromis sur le même serveur, un script mal isolé, une tâche cron exécutée avec des privilèges insuffisants ou une configuration multi-utilisateurs superficielle suffisent.
Une configuration plus correcte pour WordPress
Sur une infrastructure moderne avec Nginx et PHP-FPM par utilisateur, une configuration plus judicieuse serait la suivante :
SITE_USER="nomesito"
SITE_GROUP="web-nomesito"
SITE_PATH="/home/nomesito/public_html"
groupadd -f "$SITE_GROUP"
usermod -aG "$SITE_GROUP" nginx
usermod -aG "$SITE_GROUP" "$SITE_USER"
chown -R "$SITE_USER:$SITE_GROUP" "$SITE_PATH"
find "$SITE_PATH" -type d -exec chmod 750 {} ;
find "$SITE_PATH" -type f -exec chmod 640 {} ;
find "$SITE_PATH" -type d -exec chmod g+s {} ;
chmod 600 "$SITE_PATH/wp-config.php"
Bien entendu, il s'agit d'un exemple conceptuel, et non d'une recette à déployer aveuglément sur n'importe quel serveur. Il est indispensable de vérifier au préalable le fonctionnement de PHP-FPM : l'utilisateur sous lequel il s'exécute, le groupe principal utilisé, la manière dont les mises à jour WordPress génèrent des fichiers, le fonctionnement du système de déploiement et la présence de contrôles d'accès (ACL), de SELinux, d'AppArmor, de CageFS, d'un panneau de contrôle ou d'autres mécanismes d'isolation.
Dans certains cas, 750/640 MHz peut être plus approprié. Dans d'autres, 750/650 MHz peut être préférable si vous souhaitez conserver le bit d'exécution sur certains fichiers ou en cas de besoins opérationnels particuliers. Enfin, dans d'autres cas encore, 700/600 MHz peut être plus approprié pour les sections qui ne sont pas servies directement depuis le Web. L'objectif n'est pas d'idolâtrer un nombre, mais de cesser de considérer 755/644 comme une loi universelle.
La responsabilité des panneaux de contrôle
Plesk et cPanel ne sont pas « mauvais » parce qu'ils ne maîtrisent pas les permissions Linux. Ce sont des produits matures et complexes, utilisés dans des contextes très différents. Leur problème est tout autre : ils doivent choisir des valeurs par défaut compatibles avec le plus grand nombre de situations possible. Or, lorsqu'un logiciel doit choisir entre une sécurité rigoureuse et la réduction des problèmes de support, il privilégie souvent la seconde option.
Il en résulte qu'un paramètre conçu pour la compatibilité devient, dans l'opinion générale, une recommandation de sécurité. Et c'est dangereux. Parce que l'administrateur système inexpérimenté lit « 755 répertoires, 644 fichiers » et pense : « C'est la bonne configuration. » Ce qu'il devrait en réalité lire, c'est : « C'est la configuration qui permettra probablement d'éviter les erreurs 403 dans la plupart des environnements d'usage général. »
La différence est considérable. Une valeur par défaut n'est pas forcément une bonne pratique. Une valeur qui évite les tickets d'incident n'est pas forcément la plus sûre. Une configuration tolérée par un panneau de contrôle n'est pas nécessairement la configuration idéale pour un environnement moderne, conçu et géré par des experts.
Le cas des fichiers modifiables
Un autre sujet souvent source de confusion est celui des droits d'écriture. WordPress, les extensions, le cache, les chargements et les mises à jour nécessitent tous d'écrire dans certains répertoires. Mais cela ne signifie pas que l'intégralité du site doit être accessible en écriture ou en lecture à tous les utilisateurs.
Une gestion plus rigoureuse devrait faire la distinction entre :
- code d'application, qui ne devrait être modifiable que par le propriétaire ou le système de déploiement ;
- télécharger les répertoires, qui doivent être accessibles en écriture par le processus PHP ;
- répertoires de cache, qui doivent être accessibles en écriture par le processus de l'application ;
- des fichiers de configuration, qui doivent être aussi restrictifs que possible ;
- Les ressources statiques, que Nginx doit pouvoir lire mais pas modifier.
Une politique de gestion des permissions mature ne se contente pas de dire « tous les droits 755 et 644 ». Elle se demande : « Qui peut lire ? Qui peut écrire ? Qui peut autoriser le transit ? Qui ne doit pas y avoir accès ? » C'est seulement après cela que l'on choisit les commandes chmod, chown, les groupes, les ACL et les umasks.
Conclusion : le problème ne vient pas de Linux, mais de la paresse de ses paramètres par défaut.
Linux offre déjà tous les outils nécessaires pour bien faire les choses : utilisateurs, groupes, permissions, ACL, umask, setgid, isolation des processus, pools PHP-FPM séparés, chroot, conteneurs, espaces de noms, systèmes de contrôle d'accès comme SELinux et AppArmor. Le problème ne réside pas dans le modèle Unix, mais dans l'habitude d'utiliser des configurations laxistes sous prétexte que « c'est comme ça que ça marche ».
Historiquement, les panneaux de contrôle ont privilégié ou standardisé des permissions comme 755 et 644 car elles sont simples, compatibles et réduisent le risque de dysfonctionnement des sites mal configurés. Cependant, dans un environnement professionnel, notamment pour WordPress et plus généralement pour les sites PHP hébergés par Nginx avec un backend PHP-FPM, il existe des configurations plus correctes, plus cohérentes et plus respectueuses du principe du moindre privilège.
750 répertoires et 640 fichiers, avec une gestion des droits d'accès et des groupes appropriée, constituent un modèle plus sain. Sa mise en œuvre n'est pas toujours simple, ni sa compatibilité avec tous les panneaux de contrôle sans modifications, mais il est conceptuellement supérieur. Le serveur web ne devrait pas lire les fichiers simplement parce que « tout le monde peut lire », mais parce qu'il y est autorisé. PHP ne devrait pas écrire partout, mais uniquement là où c'est nécessaire. Les autres utilisateurs du système ne devraient pas pouvoir accéder au code et à la configuration d'un site qui ne leur appartient pas.
La véritable sécurité d'un système ne consiste pas à copier des commandes d'un guide générique, mais à comprendre le modèle d'exécution de votre infrastructure. Si le serveur est bien conçu, les ports 755 et 644 ne sont pas indispensables : il s'agit simplement d'un compromis hérité du passé. Et comme beaucoup de compromis historiques dans l'hébergement mutualisé, ils persistent non pas parce qu'ils sont justifiés, mais par commodité.