Как включить PHP-файлы, требующие абсолютного пути?

у меня есть структура каталогов, как следующее:

сценарий.в PHP

inc / include1.в PHP
inc / include2.в PHP

объекты / object1.в PHP
objects / object2.в PHP

мыло/Мыло.в PHP

теперь, я использую эти объекты в обоих script.php и /soap/soap.php, Я мог бы переместить их, но мне нужна такая структура каталогов по определенной причине. При выполнении script.php включить путь inc/include.php и при выполнении /soap/soap.php это ../inc абсолютные пути работы, /mnt/webdev/[project name]/inc/include1.php... но это уродливое решение, если я когда-нибудь хотите переместить папку в другое место.

так есть ли способ, чтобы использовать относительные пути, или способ programically создания "/mnt/webdev/[project name]/"?

11 ответов


Это должно работать

$root = realpath($_SERVER["DOCUMENT_ROOT"]);

include "$root/inc/include1.php";

Edit: добавлено imporvement by aussieviking


вы можете использовать относительные пути. Попробуй!--1-->. Это константа PHP, которая всегда возвращает путь / имя файла скрипта, в котором она находится. Итак, в soap.php, вы могли бы сделать:

include dirname(__FILE__).'/../inc/include.php';

полный путь и имя файл. Если используется внутри include, возвращается имя включенного файла. Начиная с PHP 4.0.2,__FILE__ всегда содержит абсолютный путь с символические ссылки разрешены, тогда как в более старых относительный путь (его варианты) при некоторых обстоятельствах. (источник)

другим решением было бы установить включить путь в файле httpd.conf или an .файл htaccess.


посмотрите на http://au.php.net/reserved.variables

Я думаю, что переменная вы ищете это: $_SERVER["DOCUMENT_ROOT"]


вы можете определить константу с путем к корневому каталогу вашего проекта, а затем поместить ее в начале пути.


другой способ справиться с этим, который устраняет любую потребность в includes, - использовать Автозагрузка характеристика. Включая все, что нужно вашему сценарию "на всякий случай", может помешать производительности. Если ваши includes - это все определения классов или интерфейсов, и вы хотите загружать их только при необходимости, вы можете перегрузить __autoload() функция с вашим собственным кодом, чтобы найти соответствующий файл класса и загрузить его только при вызове. Вот пример из руководство:

function __autoload($class_name) {
    require_once $class_name . '.php';
}

$obj  = new MyClass1();
$obj2 = new MyClass2(); 

пока вы устанавливаете переменные include_path соответственно, вам больше не нужно включать файл класса.


другой вариант, связанный с Кевином, - использовать __FILE__, но вместо этого замените имя файла php из него:

<?php

$docRoot = str_replace($_SERVER['SCRIPT_NAME'], '', __FILE__);
require_once($docRoot . '/lib/include.php');

?>

Я использую это на некоторое время. Единственная проблема в том, что иногда у вас нет $_SERVER['SCRIPT_NAME'], но иногда есть другая аналогичная переменная.


Я нашел, что это очень хорошо!

function findRoot() { 
    return(substr($_SERVER["SCRIPT_FILENAME"], 0, (stripos($_SERVER["SCRIPT_FILENAME"], $_SERVER["SCRIPT_NAME"])+1)));
}

использование:

<?php

function findRoot() {
    return(substr($_SERVER["SCRIPT_FILENAME"], 0, (stripos($_SERVER["SCRIPT_FILENAME"], $_SERVER["SCRIPT_NAME"])+1)));
}

include(findRoot() . 'Post.php');
$posts = getPosts(findRoot() . 'posts_content');

include(findRoot() . 'includes/head.php');

for ($i=(sizeof($posts)-1); 0 <= $i; $i--) {
    $posts[$i]->displayArticle();
}

include(findRoot() . 'includes/footer.php');

?>

Я думаю, что лучший способ-поместить ваши includes в ваш PHP include path. Существуют различные способы сделать это в зависимости от вашей установки.

затем вы можете просто обратиться к

require_once 'inc1.php';

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

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

например,

site directory
    html (web root)
        your web-accessible files
    includes
        your include files

кроме того, проверьте __autoload для ленивой загрузки файлов классов

http://www.google.com/search?q=setting + php + включить + путь

http://www.google.com/search?q=__autoload


require(str_repeat('../',(substr_count(getenv('SCRIPT_URL'),'/')-1))."/path/to/file.php");

я использую эту строку кода. Он возвращается к "вершине" дерева сайта, затем переходит к нужному файлу.

например, предположим, у меня есть это дерево файлов:

domain.com/aaa/index.php
domain.com/bbb/ccc/ddd/index.php
domain.com/_resources/functions.php

Я могу включить функции.php-файл, где бы я ни был, просто скопируйте вставку

require(str_repeat('../',(substr_count(getenv('SCRIPT_URL'),'/')-1))."/_resources/functions.php");

Если вам нужно использовать этот код много раз, вы можете создать функцию, которая возвращает str_repeat('../',(substr_count(getenv('SCRIPT_URL'),'/')-1)) часть. Затем просто вставьте эту функцию в первый файл, который вы включаете. У меня есть "инициализировать".php " файл, который я включаю в самом верху каждой страницы php и который содержит эту функцию. В следующий раз, когда я должен включить файлы, я на самом деле просто использую функцию (с именем path_back):

require(path_back()."/_resources/another_php_file.php");

@Flubba, позволяет ли это мне иметь папки внутри моего каталога include? плоские каталоги include дают мне кошмары. поскольку весь каталог объектов должен находиться в каталоге inc.

О да, абсолютно. Так, например, мы используем один слой вложенных папок, как правило:

require_once('library/string.class.php')

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

так, например, если вы делаете MVC, вы бы поместили путь к вашему приложению directoy в Include path, а затем указали ссылку на вещи в форме

'model/user.class'
'controllers/front.php'

или что-то еще.

но вообще говоря, он просто позволяет работать с очень короткими путями в вашем PHP, которые будут работать из любого места и это намного проще для чтения, чем весь этот документ realpath root malarkey.

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


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

define("APPLICATION_PATH", realpath(dirname(__FILE__) . '/../app'));
or 
define("APPLICATION_PATH", realpath(DIR(__FILE__) . '/../app'));

теперь эта глобальная переменная"APPLICATION_PATH " можно использовать для включения всех файлов вместо вызова realpath () каждый раз, когда вы включаете новый файл.

EX:

include(APPLICATION_PATH ."/config/config.ini";

надеюсь, что это помогает ;-)