我已经搜索了高和低,得到了很多不同的解决方案和变量包含信息,以获得绝对路径。但它们似乎在某些条件下有效,而在其他条件下无效。有没有一种银弹方法来获得在PHP中执行的脚本的绝对路径?对我来说,脚本将从命令行运行,但是,如果在Apache等中运行,解决方案应该也能正常运行。

澄清:最初执行的脚本,不一定是编码解决方案的文件。


当前回答

__FILE__常量将给你当前文件的绝对路径。

更新:

问题被更改为询问如何检索最初执行的脚本,而不是当前运行的脚本。唯一(??)可靠的方法是使用debug_backtrace函数。

$stack = debug_backtrace();
$firstFrame = $stack[count($stack) - 1];
$initialFile = $firstFrame['file'];

其他回答

有一个简单的方法来获得初始执行脚本的绝对路径,在该脚本和包含include, require, require_once的任何其他脚本中,使用一个常量并将当前脚本路径存储在主脚本的开头:

define( 'SCRIPT_ROOT', __FILE__ );

上面的解决方案适用于当有一个单一的“主”脚本,包括所有其他需要的脚本,如在大多数web应用程序,工具和shell脚本。

如果不是这样,可能会有几个“初始脚本”,那么为了避免重新定义,并在常量中存储正确的路径,每个脚本可能以以下方式开始:

if( ! defined( 'SCRIPT_ROOT' ) ) {
    define( 'SCRIPT_ROOT`, __FILE__ );
}

关于(目前)接受的答案的说明:

答案表明最初执行的脚本路径是get_included_files()返回的数组的第一个元素。

这是一个聪明而简单的解决方案——在撰写本文时——(我们已经接近PHP 7.4.0了)它确实有效。

但是,通过查看文档,并没有提到最初执行的脚本是get_included_files()返回的数组的第一项。

我们只读书

最初调用的脚本被认为是一个“包含文件”,因此它将与include和family引用的文件一起列出。

在编写的时候,“脚本最初被调用”是数组中的第一个,但是-技术上-不能保证这在未来不会改变。


关于realpath(), __FILE__和__DIR__的说明:

其他人在他们的回答中建议使用__FILE__, __DIR__, dirname(__FILE__), realpath(__DIR__)…

dirname(__FILE__)等于__DIR__(在PHP 5.3.0中引入),因此只需使用__DIR__。

__FILE__和__DIR__都是绝对路径,因此realpath()是不必要的。

如果你想获取当前工作目录,请使用getcwd()

http://php.net/manual/en/function.getcwd.php

__FILE__将返回路径和文件名,例如在XAMPP上C:\ XAMPP \htdocs\index.php而不是C:\ XAMPP \htdocs\

echo realpath(dirname(__FILE__));

如果将此文件放在包含的文件中,它将打印该包含的路径。要获得父脚本的路径,将__FILE__替换为$_SERVER['PHP_SELF']。但是请注意PHP_SELF是一个安全风险!

这是我为此写的一个有用的PHP函数。正如最初的问题所阐明的那样,它返回执行初始脚本的路径——而不是我们当前所在的文件。

/**
 * Get the file path/dir from which a script/function was initially executed
 * 
 * @param bool $include_filename include/exclude filename in the return string
 * @return string
 */ 
function get_function_origin_path($include_filename = true) {
    $bt = debug_backtrace();
    array_shift($bt);
    if ( array_key_exists(0, $bt) && array_key_exists('file', $bt[0]) ) {
        $file_path = $bt[0]['file'];
        if ( $include_filename === false ) {
            $file_path = str_replace(basename($file_path), '', $file_path);
        }
    } else {
        $file_path = null;
    }
    return $file_path;
}
realpath($_SERVER['SCRIPT_FILENAME'])

对于在web服务器$_SERVER['SCRIPT_FILENAME']下运行的脚本,将包含最初调用脚本的完整路径,因此可能是你的index.php。在本例中不需要Realpath()。

对于从控制台运行的脚本,$_SERVER['SCRIPT_FILENAME']将包含从当前工作目录到最初调用脚本的相对路径。因此,除非你在脚本中更改了工作目录,否则它将解析为绝对路径。