1

简短版本:
相对路径如何在 php 中工作?


长版:
我有一个本地网站 ( http://test.com ) 并且E:\test\ 是它的文档根目录。这是我的目录树:

  1. E:\test\001.php
  2. E:\test\exit.php
  3. E:\test\death.txt
  4. E:\test\mysql\first.php
  5. E:\test\mysql\death.txt
  6. E:\test\mysql\exit.php

和文件内容:

E:\test\001.php

<?php

include('mysql/first.php');

?>

E:\test\exit.php

<?php
die('What?');
?>

E:\test\death.txt

Bonjour

E:\test\mysql\first.php

<?php
echo file_get_contents('death.txt');
include('exit.php');
?>

E:\test\mysql\death.txt

Hello there

E:\test\mysql\exit.php

<?php
die('DONE');
?>

如果我浏览http://test.com/001.php 并存在,我会得到这个E:\test\exit.phpE:\test\death.txt

BonjourWhat?

如果它们不存在:

Warning: file_get_contents(death.txt) [function.file-get-contents]: failed to open stream: No such file or directory in E:\test\mysql\first.php on line 2
DONE

相对路径如何在 php 中工作?我认为它应该给我两个文件的警告或显示正确的输出!
我正在使用 XAMPP、php 5.3 在 Win7 x64 上测试此代码。

4

2 回答 2

3

php.net 上的文档是这样描述 PHPinclude搜索机制的:

  1. 首先,它将查看 include_path: http: //php.net/manual/en/ini.core.php#ini.include-path
  2. 然后,如果在 include_path 中找不到任何内容,它将尝试将文件加载到调用脚本自己的目录中。(在我们的例子中,根目录)
  3. 最后,如果一切都失败了,它将尝试在当前目录中查找文件。

当我运行你的脚本时,我的包含路径.:默认设置为(当前目录,没有别的),所以当我尝试加载death.txtexit.php从中mysql/first.php搜索时,应该在./当前目录的文件夹中搜索。但是......它没有。当前目录应该是mysql/但它没有指向那里......那么这里发生了什么?

PHP 在这方面很特别……让我们回滚到我们所做的第一条语句。PHP在我们include path使用的时候解释的.是什么,实际上又是一个路径解析!所以,看看我们的路径,我们有.哪些不能被解释(./.再次?)使用我们的 include_path 的任何东西。然后,PHP 必须转到第二个路径解析 (2),它是我们脚本的根目录。(你有头疼了吗?因为我有)

使用get_include_path()并且realpath()您可以观察到这一点:

Included path: '.:'
Including mysql/first.php: /Users/Kouno/Development/SandBox/test-php/mysql/first.php
This is what `realpath` returns for './': /Users/Kouno/Development/SandBox/test-php
Getting content of death.txt: /Users/Kouno/Development/SandBox/test-php/death.txt
Bonjour
Including exit.php: /Users/Kouno/Development/SandBox/test-php/exit.php
What?

那么,为什么一旦你从根目录中删除它,它仍然无法加载mysql/death.txt但仍然 find ?它应该找到他们两个,对吧?mysql/exit.phpdeath.txtexit.php

嗯,这是因为get_file_content有第二个参数include_path默认忽略。

如果设置第二个参数:

echo file_get_contents('death.txt', FILE_USE_INCLUDE_PATH);

然后你会得到预期的结果。

Included path: '.:'
Including mysql/first.php: /Users/Kouno/Development/SandBox/test-php/mysql/first.php
Getting content of death.txt: (no path returned)
Hello there
Including exit.php: (no path returned)
DONE

有趣的是,get_file_content()它将开始使用相同的机制include(这在 php.net 上没有正确记录)。realpath()甚至根本没有实现这个机制(这就解释了为什么我会出现no path returned)。

希望这可以帮助!

于 2013-01-27T03:59:08.757 回答
0

first.php 在 E:\test\mysql 中找到文件 death.txt。您可以使用:

echo file_get_contents($_SERVER['DOCUMENT_ROOT'] . DIRECTORY_SEPARATOR . 'death.txt');

或者:

echo file_get_contents('..' . DIRECTORY_SEPARATOR . 'death.txt');
于 2013-01-27T02:25:56.243 回答