Maison > Questions et réponses > le corps du texte
P粉3620719922023-08-24 12:18:48
Ajouté à la (très bonne) réponse existante
open_basedir
可能会难倒您,因为它可以在 Web 服务器配置中指定。虽然如果您运行自己的专用服务器,这很容易解决,但有一些共享托管软件包(如 Plesk、cPanel 等)可以在每个域的基础上配置配置指令。由于该软件会构建配置文件(即 httpd.conf
), vous ne pouvez donc pas modifier ce fichier directement car le logiciel d'hébergement l'écrasera simplement au redémarrage.
Avec Plesk, ils fournissent un emplacement pour couvrir ce qu'ils ont à offrir httpd.conf
(称为 vhost.conf
). Seuls les administrateurs du serveur peuvent écrire dans ce fichier. La configuration Apache ressemble à ceci
<Directory /var/www/vhosts/domain.com> <IfModule mod_php5.c> php_admin_flag engine on php_admin_flag safe_mode off php_admin_value open_basedir "/var/www/vhosts/domain.com:/tmp:/usr/share/pear:/local/PEAR" </IfModule> </Directory>
Demandez à votre administrateur de serveur de consulter les manuels des logiciels d'hébergement et de serveur Web qu'il utilise.
Il est important de noter que l’exécution de fichiers via un serveur Web est très différente de l’exécution d’une ligne de commande ou d’une tâche cron. La plus grande différence est que votre serveur Web possède ses propres utilisateurs et autorisations. Cet utilisateur est fortement restreint pour des raisons de sécurité. Par exemple, Apache est généralement apache
、www-data
或 httpd
(selon votre serveur). Une tâche cron ou une exécution CLI a toutes les autorisations dont dispose l'utilisateur qui l'exécute (c'est-à-dire qu'un script PHP exécuté en tant que root s'exécutera avec les autorisations root).
Souvent, les gens résolvent les problèmes d'autorisation en procédant comme suit (exemple Linux)
chmod 777 /path/to/file
Ce n'est pas une bonne idée car le fichier ou le répertoire est désormais accessible en écriture par tout le monde. Si vous possédez le serveur et êtes le seul utilisateur, ce n'est pas grave, mais si vous êtes dans un environnement d'hébergement partagé, vous accordez l'accès à tout le monde sur le serveur.
Ce que vous devez faire est d'identifier les utilisateurs qui ont besoin d'un accès et de leur accorder l'accès uniquement. Une fois que vous savez quels utilisateurs ont besoin d'accéder, vous devez vous en assurer
Cet utilisateur est propriétaire du fichier et possède probablement le répertoire parent (en particulier le répertoire parent si vous écrivez dans le fichier). Dans la plupart des environnements d'hébergement partagé, cela ne posera pas de problème puisque votre utilisateur doit être propriétaire de tous les fichiers du répertoire racine. Un exemple Linux est présenté ci-dessous
chown apache:apache /path/to/file
Cet utilisateur (et uniquement cet utilisateur) a accès. Sous Linux, une bonne pratique est chmod 600
(只有所有者可以读写)或 chmod 644
(le propriétaire peut écrire, mais tout le monde peut lire)
Vous pouvez lire une discussion plus large sur les autorisations et les utilisateurs Linux/Unix ici
P粉2686548732023-08-24 00:48:10
Il existe de nombreuses raisons pour lesquelles vous pouvez rencontrer cette erreur, donc une bonne liste de contrôle de ce qu'il faut vérifier en premier peut être utile.
Supposons que nous résolvions la ligne suivante :
require "/path/to/file"
Ou déplacez l'appel de require*
或 include*
dans sa propre variable, faites-lui écho, copiez-le et essayez d'y accéder depuis le terminal :
$path = "/path/to/file"; echo "Path : $path"; require "$path";
Puis, dans le terminal :
cat <file path pasted>
/users/tony/htdocs
Pour rendre votre script robuste lors du déplacement de contenu tout en générant des chemins absolus au moment de l'exécution, vous avez 2 options :
require __DIR__ 。 “/相对/路径/来自/当前/文件”
。 __DIR__
pour renvoyer le répertoire du fichier actuel.
constante : SITE_ROOT
config.php
dans config.php
define('SITE_ROOT', __DIR__);
, puis utilisez la constante config.php
,然后在任意位置使用 SITE_ROOT
n'importe où : p>
require_once __DIR__."/../config.php"; ... require_once SITE_ROOT."/other/file.php";
Ces 2 pratiques rendent également votre application plus portable car elle ne repose pas sur les paramètres ini tels que les chemins d'inclusion.
Une autre façon d'inclure des fichiers, qui n'est ni relative ni purement absolue, consiste à s'appuyer sur le chemin d'inclusion. C'est souvent le cas des bibliothèques ou des frameworks tels que Zend Framework.
Une telle inclusion ressemblerait à ceci :
include "Zend/Mail/Protocol/Imap.php"
Dans ce cas, vous devez vous assurer que le dossier où se trouve "Zend" fait partie du chemin d'inclusion.
Vous pouvez vérifier le chemin d'inclusion à l'aide de la commande suivante :
echo get_include_path();
Vous pouvez y ajouter des dossiers en utilisant la commande suivante :
set_include_path(get_include_path().":"."/path/to/new/folder");
Pour résumer, l'utilisateur qui exécute le processus serveur (Apache ou PHP) peut ne pas avoir du tout l'autorisation de lire ou d'écrire le fichier.
Pour vérifier sous quel utilisateur le serveur s'exécute, vous pouvez utiliser posix_getpwuid< /一> :
$user = posix_getpwuid(posix_geteuid()); var_dump($user);
Pour retrouver les permissions d'un fichier, tapez la commande suivante dans le terminal :
ls -l <path/to/file>
Et consultez la notation d'autorisation
Si aucune des méthodes ci-dessus ne fonctionne, le problème peut être que certains paramètres PHP l'empêchent d'accéder au fichier.
Trois paramètres peuvent être pertinents :
phpinfo()
phpinfo()
或使用 ini_get("open_basedir")
ou en utilisant ini_get("open_basedir")
ini_get("allow_url_include")
检查并使用 ini_set("allow_url_include", "1")
ParamètresSi aucune des méthodes ci-dessus ne permet de diagnostiquer le problème, certaines des situations particulières suivantes peuvent se produire :
Vous pouvez inclure une bibliothèque, telle que le framework Zend, en utilisant un chemin relatif ou absolu. Par exemple :
require "/usr/share/php/libzend-framework-php/Zend/Mail/Protocol/Imap.php"
Mais vous rencontrerez toujours le même type d’erreurs.
Cela se produit parce que le fichier que vous incluez (avec succès) lui-même a une instruction d'inclusion provenant d'un autre fichier, et la deuxième instruction d'inclusion suppose que vous avez ajouté le chemin d'accès à la bibliothèque au chemin d'inclusion.
Par exemple, le fichier du framework Zend mentionné précédemment peut contenir les éléments suivants :
include "Zend/Mail/Protocol/Exception.php"
Ni inclus via un chemin relatif ni inclus via un chemin absolu. On suppose que le répertoire du framework Zend a été ajouté au chemin d'inclusion.
Dans ce cas, la seule solution pratique est d'ajouter le répertoire au chemin d'inclusion.
Si vous utilisez Linux à sécurité renforcée, cela peut être la cause du problème, car l'accès au fichier depuis le serveur est refusé.
Pour vérifier si SELinux est activé sur votre système, exécutez la commande sestatus
dans le terminal. Si cette commande n'existe pas, SELinux n'existe pas sur votre système. S'il existe, il devrait vous indiquer s'il est appliqué.
Pour vérifier si la politique SELinux est à l'origine du problème, vous pouvez essayer de la désactiver temporairement. Mais soyez prudent car cela désactivera complètement la protection. Ne faites pas cela sur un serveur de production.
setenforce 0
Si vous n'avez plus de problèmes après avoir désactivé SELinux, alors c'est la cause première.
Pour résoudre ce problème, vous devez configurer SELinux en conséquence.
Les types de contexte suivants sont requis :
httpd_sys_content_t
pour les fichiers que vous souhaitez que le serveur puisse lirehttpd_sys_rw_content_t
pour les fichiers auxquels vous souhaitez accéder en lecture et en écriture httpd_log_t
pour les fichiers journauxhttpd_cache_t
pour le répertoire de cachePar exemple, pour attribuer le type de contexte httpd_sys_content_t
à la racine de votre site Web, exécutez :
semanage fcontext -a -t httpd_sys_content_t "/path/to/root(/.*)?" restorecon -Rv /path/to/root
Si votre fichier se trouve dans votre répertoire personnel, vous devrez également ouvrir httpd_enable_homedirs
Booléen :
setsebool -P httpd_enable_homedirs 1
Quoi qu'il en soit, il peut y avoir plusieurs raisons pour lesquelles SELinux refuse l'accès à un fichier, en fonction de votre stratégie. Vous devez donc enquêter là-dessus. Voici un tutoriel spécifiquement pour configurer SELinux pour votre serveur Web.
Si vous utilisez Symfony et que vous rencontrez cette erreur lors du téléchargement sur le serveur, il est possible que le cache de votre application n'ait pas été réinitialisé depuis le téléchargement de app/cache
, ou que le cache n'ait pas encore été vidé.
Vous pouvez tester et résoudre ce problème en exécutant la commande de console suivante :
cache:clear
Apparemment, cette erreur se produit également lors de l'appel de zip->close()
lorsque certains fichiers du zip contiennent des caractères non-ASCII (par exemple "é") dans leurs noms de fichiers.
Une solution possible consiste à envelopper le nom de fichier dans utf8_decode()
avant de créer le fichier cible.
Merci à Fran Cano d'avoir identifié ce problème et proposé une solution< /p>