Rumah > Soal Jawab > teks badan
P粉3620719922023-08-24 12:18:48
Ditambah pada (sangat baik) jawapan sedia ada
open_basedir
可能会难倒您,因为它可以在 Web 服务器配置中指定。虽然如果您运行自己的专用服务器,这很容易解决,但有一些共享托管软件包(如 Plesk、cPanel 等)可以在每个域的基础上配置配置指令。由于该软件会构建配置文件(即 httpd.conf
), jadi anda tidak boleh menukar fail itu secara langsung kerana perisian pengehosan hanya akan menimpanya semasa but semula.
Dengan Plesk, mereka menyediakan lokasi untuk menampung apa yang mereka tawarkan httpd.conf
(称为 vhost.conf
). Hanya pentadbir pelayan boleh menulis ke fail ini. Konfigurasi Apache kelihatan seperti ini
<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>
Minta pentadbir pelayan anda untuk merujuk manual untuk perisian pengehosan dan pelayan web yang mereka gunakan.
Adalah penting untuk ambil perhatian bahawa melaksanakan fail melalui pelayan web adalah sangat berbeza daripada baris arahan atau pelaksanaan tugas cron. Perbezaan terbesar ialah pelayan web anda mempunyai pengguna dan kebenarannya sendiri. Pengguna ini sangat dihadkan atas sebab keselamatan. Contohnya, Apache biasanya apache
、www-data
或 httpd
(bergantung pada pelayan anda). Tugas cron atau pelaksanaan CLI mempunyai apa sahaja kebenaran yang dimiliki oleh pengguna yang menjalankannya (iaitu skrip PHP yang dijalankan sebagai root akan dilaksanakan dengan kebenaran root).
Banyak kali orang menyelesaikan masalah kebenaran dengan melakukan perkara berikut (contoh Linux)
chmod 777 /path/to/file
Ini bukan idea yang bijak kerana fail atau direktori kini boleh ditulis secara global. Jika anda memiliki pelayan dan merupakan satu-satunya pengguna, ini bukan masalah besar, tetapi jika anda berada dalam persekitaran pengehosan yang dikongsi, anda memberikan akses kepada semua orang pada pelayan.
Apa yang anda perlu lakukan ialah mengenal pasti pengguna yang memerlukan akses dan berikan akses kepada mereka sahaja. Sebaik sahaja anda mengetahui pengguna mana yang memerlukan akses, anda perlu memastikan
Pengguna ini memiliki fail dan berkemungkinan memiliki direktori induk (terutamanya direktori induk jika anda menulis ke fail). Dalam kebanyakan persekitaran pengehosan yang dikongsi ini tidak akan menjadi masalah kerana pengguna anda harus memiliki semua fail dalam direktori akar. Contoh Linux ditunjukkan di bawah
chown apache:apache /path/to/file
Pengguna ini (dan hanya pengguna ini) mempunyai akses. Dalam Linux, amalan yang baik ialah chmod 600
(只有所有者可以读写)或 chmod 644
(pemilik boleh menulis, tetapi semua orang boleh membaca)
Anda boleh membaca perbincangan yang lebih luas tentang Kebenaran dan Pengguna Linux/Unix di sini
P粉2686548732023-08-24 00:48:10
Terdapat banyak sebab mengapa anda mungkin menghadapi ralat ini, jadi senarai semak yang baik tentang perkara yang perlu diperiksa dahulu boleh membantu.
Andaikan kami sedang menyelesaikan masalah baris berikut:
require "/path/to/file"
Atau alihkan apa sahaja panggilan require*
或 include*
ke dalam pembolehubahnya sendiri, gemakannya, salinnya dan cuba aksesnya dari terminal:
$path = "/path/to/file"; echo "Path : $path"; require "$path";
Kemudian, di terminal:
cat <file path pasted>
/users/tony/htdocs
Untuk menjadikan skrip anda mantap apabila memindahkan kandungan sambil masih menjana laluan mutlak pada masa jalanan, anda mempunyai 2 pilihan:
require __DIR__ 。 “/相对/路径/来自/当前/文件”
。 __DIR__
untuk mengembalikan direktori fail semasa.
malar: SITE_ROOT
config.php
dalam config.php
define('SITE_ROOT', __DIR__);
, kemudian gunakan pemalar config.php
,然后在任意位置使用 SITE_ROOT
di mana-mana sahaja: p>
require_once __DIR__."/../config.php"; ... require_once SITE_ROOT."/other/file.php";
2 amalan ini juga menjadikan aplikasi anda lebih mudah alih kerana ia tidak bergantung pada tetapan ini seperti laluan sertakan.
Cara lain untuk memasukkan fail, yang bukan relatif atau mutlak semata-mata, adalah dengan bergantung pada laluan serta. Ini selalunya berlaku dengan perpustakaan atau rangka kerja seperti Rangka Kerja Zend.
Pemasukan sedemikian akan kelihatan seperti ini:
include "Zend/Mail/Protocol/Imap.php"
Dalam kes ini, anda perlu memastikan bahawa folder tempat "Zend" terletak adalah sebahagian daripada laluan sertakan.
Anda boleh menyemak laluan sertakan menggunakan arahan berikut:
echo get_include_path();
Anda boleh menambah folder padanya menggunakan arahan berikut:
set_include_path(get_include_path().":"."/path/to/new/folder");
Untuk meringkaskan, pengguna yang menjalankan proses pelayan (Apache atau PHP) mungkin tidak mempunyai kebenaran untuk membaca atau menulis fail sama sekali.
Untuk menyemak pengguna mana pelayan sedang berjalan, anda boleh menggunakan posix_getpwuid< /一>:
$user = posix_getpwuid(posix_geteuid()); var_dump($user);
Untuk mencari kebenaran fail, taip arahan berikut dalam terminal:
ls -l <path/to/file>
Dan lihat notasi kebenaran
Jika tiada kaedah di atas berfungsi, masalahnya mungkin beberapa tetapan PHP menghalangnya daripada mengakses fail.
Tiga tetapan mungkin berkaitan:
phpinfo()
phpinfo()
或使用 ini_get("open_basedir")
atau menggunakan ini_get("open_basedir")
ini_get("allow_url_include")
检查并使用 ini_set("allow_url_include", "1")
TetapanJika tiada kaedah di atas dapat mendiagnosis masalah, beberapa situasi khas berikut mungkin berlaku:
Anda mungkin menyertakan perpustakaan, seperti rangka kerja Zend, menggunakan laluan relatif atau mutlak. Contohnya:
require "/usr/share/php/libzend-framework-php/Zend/Mail/Protocol/Imap.php"
Tetapi anda masih akan menghadapi jenis ralat yang sama.
Ini berlaku kerana fail yang anda (berjaya) sertakan sendiri mempunyai pernyataan include daripada fail lain, dan pernyataan include kedua menganggap bahawa anda telah menambahkan laluan ke pustaka ke laluan include.
Sebagai contoh, fail rangka kerja Zend yang dinyatakan sebelum ini mungkin mengandungi perkara berikut:
include "Zend/Mail/Protocol/Exception.php"
Tidak disertakan melalui laluan relatif atau disertakan melalui laluan mutlak. Diandaikan bahawa direktori rangka kerja Zend telah ditambahkan pada laluan termasuk.
Dalam kes ini, satu-satunya penyelesaian praktikal ialah menambah direktori pada laluan sertakan.
Jika anda menjalankan Linux yang dipertingkatkan keselamatan, maka ini mungkin punca masalah, kerana akses kepada fail daripada pelayan dinafikan.
Untuk menyemak sama ada SELinux didayakan pada sistem anda, jalankan arahan sestatus
dalam terminal. Jika arahan ini tidak wujud, SELinux tidak wujud pada sistem anda. Jika ia wujud, maka ia harus memberitahu anda sama ada ia dikuatkuasakan.
Untuk menyemak sama ada polisi SELinux adalah punca masalah, anda boleh cuba mematikannya buat sementara waktu. Tetapi berhati-hati kerana ini akan melumpuhkan perlindungan sepenuhnya. Jangan lakukan ini pada pelayan pengeluaran.
setenforce 0
Jika anda tidak lagi menghadapi masalah selepas mematikan SELinux, maka inilah puncanya.
Untuk menyelesaikan isu ini, anda mesti mengkonfigurasi SELinux dengan sewajarnya.
Jenis konteks berikut diperlukan:
httpd_sys_content_t
untuk fail yang anda mahu pelayan boleh membacahttpd_sys_rw_content_t
untuk fail yang anda mahu akses baca dan tulis httpd_log_t
untuk fail loghttpd_cache_t
untuk direktori cacheSebagai contoh, untuk menetapkan jenis konteks httpd_sys_content_t
kepada akar tapak web anda, jalankan:
semanage fcontext -a -t httpd_sys_content_t "/path/to/root(/.*)?" restorecon -Rv /path/to/root
Jika fail anda terletak dalam direktori rumah anda, anda juga perlu membuka httpd_enable_homedirs
Boolean:
setsebool -P httpd_enable_homedirs 1
Apapun, mungkin terdapat beberapa sebab mengapa SELinux menafikan akses kepada fail, bergantung pada strategi anda. Jadi anda perlu menyiasat perkara ini. Di sini ialah tutorial khusus untuk mengkonfigurasi SELinux untuk pelayan web anda.
Jika anda menggunakan Symfony dan anda menghadapi ralat ini semasa memuat naik ke pelayan, mungkin cache apl anda belum ditetapkan semula sejak app/cache
telah dimuat naik atau cache belum dikosongkan lagi.
Anda boleh menguji dan membetulkan isu ini dengan menjalankan arahan konsol berikut:
cache:clear
Nampaknya ralat ini juga berlaku semasa memanggil zip->close()
apabila beberapa fail dalam zip mengandungi aksara bukan ASCII (cth. "é") dalam nama failnya.
Penyelesaian yang mungkin adalah dengan membungkus nama fail dalam utf8_decode()
sebelum mencipta fail sasaran.
Terima kasih kepada Fran Cano kerana mengenal pasti isu ini dan mencadangkan penyelesaian< /p>