2

我的 Windows 服务器上有一个符号链接,它是这样制作的:

F:\>mkdir link-target
F:\>mklink /D link f:\link-target 

f:(注意符号链接目标中的小写字母)

在 PHP 中我运行这个:

$dir = realpath('f:\link');
var_dump($dir);

$dir = realpath($dir);
var_dump($dir);

哪个输出:

string 'f:\link-target' (length=14)
string 'F:\link-target' (length=14)

注意第二个真实路径上大小写的变化。

这是一个错误,还是有意的?解决它的最佳方法是什么?

它正在打破这样的案例:

function check_link($to, $from) {
    if (realpath($to) !== realpath($from)) {
        ...
    }
}

用于检查是否$to存在,并链接到$from.

  • PHP 5.4
  • Windows 7的

编辑:

我需要在 Windows 和 Linux 上保持一致的行为,并且有以下工作非常讨厌:

if (realpath($from) === false) {
} elseif (realpath($to) === false) {
} else {
    do {
        $to = realpath($to);
    } while (realpath($to) !== false && $to !== realpath($to));
    do {
        $from = realpath($from);
    } while (realpath($from) !== false && $from !== realpath($from));
    if ($to !== $from) {
        ...
    }
}

编辑2:

在进一步调查中,我注意到在 Windows 上,符号链接仅被跟踪 1 级:

// F:\>mkdir link-target
// F:\>mklink /D link f:\link-target 
// F:\>mklink /D link2 f:\link

$dir = realpath('f:\link2');
var_dump($dir);

$dir = realpath($dir);
var_dump($dir);

$dir = realpath($dir);
var_dump($dir);

// string 'f:\link' (length=7)
// string 'f:\link-target' (length=14)
// string 'F:\link-target' (length=14)
4

2 回答 2

1

原来

do {
    $to = realpath($to);
} while (realpath($to) !== false && $to !== realpath($to));

是唯一的方法。

https://bugs.php.net/bug.php?id=61933

于 2012-05-07T20:19:40.800 回答
0

这是有道理的,如果你仔细考虑的话。对于第一个路径解析,它正在查找定义为链接目标的内容。对于第二个,您最终会得到相同的路径,但驱动器号的大写字母正确。

在 Windows 文件系统下,路径/文件名不区分大小写。要比较它们,只需在测试前将两者都转换为大写或小写。

if (strtoupper(realpath($to)) !== strtotupper(realpath($from))) {
于 2012-05-02T17:22:19.447 回答