Как получить исходный путь символической ссылки в PHP?

У меня есть несколько файлов в веб-папке, включая эти два:

  • / mydocroot / include / somesubdir / include.Инк.в PHP
  • /mydocroot/include / настройки.Инк.в PHP

здесь somesubdir - символическая ссылка на другой каталог на моем диске, на путь с именем, скажем /в любом месте/другое.

внутри включить.Инк.в PHP, что-то вроде этого написано:

<?php

require_once "../settings.inc.php";

?>

в моем мнение, что должны включить /mydocroot/включить/настройки.в PHP... Но угадайте, что происходит: PHP пытается включить /в любом месте/настройки.Инк.в PHP, вместо /mydocroot/включить/настройки.Инк.в PHP.

похоже, что PHP автоматически разрешает символические ссылки.

Как я могу избежать этого и включить мой настройки.Инк.в PHP?

4 ответов


самое прямое решение-всегда использовать абсолютные пути. Есть несколько способов сделать это: от жесткого кодирования пути каждый раз, когда вам это нужно, до жесткого кодирования пути один раз в верхней части вашего скрипта и ссылки на это, чтобы динамически выяснить его и установить его один раз в верхней части вашего скрипта.

третий вариант-это то, что большинство готовых CMSs используют, чтобы иметь возможность работать без полного знания вашей файловой структуры.

Почему это вы используете символически связанный каталог таким образом?


у меня просто была аналогичная проблема. Вы можете сделать это с помощью $_SERVER['SCRIPT_FILENAME'] переменная, которая отображает запрошенный файл, поэтому в вашем случае это будет /mydocroot/include/somesubdir/include.inc.php, даже если somesubdir является символической ссылкой. Чтобы включить файл, который на один уровень ниже, а не делать

require_once "../settings.inc.php";

этого:

require_once dirname(dirname($_SERVER['SCRIPT_FILENAME'])).DIRECTORY_SEPARATOR."settings.inc.php"

документация о $_SERVER переменные


решение заключается в создании переменной basepath. Лучший способ сделать это-включить следующее в верхней части вашего скрипта, а затем ссылаться на него

$basepath = dirname(dirname($_SERVER['SCRIPT_FILENAME'])).DIRECTORY_SEPARATOR;

затем вы можете ссылаться на basepath в своем includes, requires и т. д. Следовательно,

include "../myscript.php";

стал

include $basepath."myscript.php";

если вы вернулись тикают дальше, вы будете иметь это:

include "../../myscript.php";

стал

include $basepath."../myscript.php";

вы должны вложить функции dir_name дважды, плюс еще один раз для каждой дополнительной папки, которую вам нужно прокрутить. Вы должны вернуться в папку, где существует символическая ссылка.

Я считаю эту проблему основным недостатком дизайна с PHP. Я не могу придумать ни одного экземпляра, где был бы желателен доступ к backticked файлам относительно фактического файла. Во всех ситуациях, включая виртуальный хостинг, имеет смысл только регрессировать назад по связанному пути, но не по целевому пути.


можно использовать is_link чтобы проверить, является ли файл символической ссылкой. Если это так, используйте readlink чтобы получить абсолютную цель.

но за десять лет разработки php у меня никогда не было причин использовать символические ссылки. Как предполагает Джейсон, я всегда определял или выводил абсолютный путь один раз, а затем использовал его в своем приложении, чтобы сделать все пути к файлам абсолютными.