Настройка корневого пути WWW для PHP на сервере

Раздел: Администрирование -> Настройка сервера

Основное решение: настройка DocumentRoot в Apache или root в Nginx

Наиболее эффективный способ определить корневую директорию WWW для PHP - задать правильный DocumentRoot (Apache) или root (Nginx). Это напрямую влияет на значение $_SERVER['DOCUMENT_ROOT'] и определяет, из какой папки сервер отдаёт файлы.

Для Apache отредактируйте файл виртуального хоста (например, /etc/apache2/sites-available/example.conf):

<VirtualHost *:80>
    ServerName example.com
    DocumentRoot /var/www/example/public_html
    <Directory /var/www/example/public_html>
        Options Indexes FollowSymLinks
        AllowOverride All
        Require all granted
    </Directory>
</VirtualHost>

Для Nginx в блоке server (файл /etc/nginx/sites-available/example):

server {
    listen 80;
    server_name example.com;
    root /var/www/example/public_html;
    index index.php index.html;
    location ~ \.php$ {
        include snippets/fastcgi-php.conf;
        fastcgi_pass unix:/var/run/php/php8.1-fpm.sock;
    }
}

Пояснение: DocumentRoot или root указывают, где искать файлы для данного домена. PHP-скрипты выполняются относительно этой папки. Изменяя эту директиву, вы меняете корень WWW для проекта.

Типичные ошибки

  • Несовпадение путей: если DocumentRoot указан неверно, сервер выдаёт 404.
  • Забыли перезагрузить сервер: sudo systemctl reload apache2 или sudo nginx -s reload.
  • Проблемы с правами доступа: папка должна быть доступна для чтения веб-серверу (обычно пользователь www-data).

Как изменить корень WWW с помощью PHP built-in server для разработки?

Встроенный сервер PHP позволяет быстро задать корневую директорию через аргумент командной строки:

php -S localhost:8080 -t /home/user/myproject/public

Флаг -t определяет корневую папку. Все запросы будут обрабатываться относительно неё. Это удобно для изолированной разработки без полноценного веб-сервера.

Проблемы

  • Не подходит для production - нет многопоточности и оптимизации.
  • Не поддерживает .htaccess.

Как задать корень WWW через символическую ссылку на папку проекта?

Можно создать символическую ссылку в существующей корневой директории (например, /var/www/html) на реальную папку проекта:

ln -s /home/user/project/public /var/www/html/myproject

Теперь URL http://example.com/myproject ведёт к файлам из /home/user/project/public. PHP-скрипты будут видеть корень как /var/www/html, но содержимое будет браться из связанной папки. Этот метод полезен, когда нужно временно подключить проект без изменения конфигурации сервера.

Типичные ошибки

  • Символическая ссылка только для чтения, если не настроен FollowSymLinks (включите его в конфигурации Apache или Nginx).
  • Путаница с относительными путями в PHP: $_SERVER['DOCUMENT_ROOT'] всё равно указывает на /var/www/html, а не на реальную папку.

Как изменить корень WWW с помощью Alias в Apache или Nginx?

Директива Alias (Apache) или alias (Nginx) позволяет привязать URL-путь к произвольной директории, не меняя DocumentRoot. Пример для Apache:

<VirtualHost *:80>
    ServerName example.com
    DocumentRoot /var/www/html
    Alias /blog /home/user/blog/public
    <Directory /home/user/blog/public>
        Require all granted
    </Directory>
</VirtualHost>

Теперь /blog ведёт к другой корневой директории. Для Nginx:

location /blog/ {
    alias /home/user/blog/public/;
    index index.php;
    location ~ \.php$ {
        fastcgi_pass unix:/var/run/php/php8.1-fpm.sock;
        include fastcgi_params;
        fastcgi_param SCRIPT_FILENAME $request_filename;
    }
}

Этот вариант подходит, когда нужно разместить несколько проектов под одним доменом, не меняя корневой DocumentRoot.

Ошибки

  • В Nginx alias и location с регулярными выражениями могут конфликтовать, нужно аккуратно указывать пути.
  • PHP не всегда корректно определяет $_SERVER['DOCUMENT_ROOT'] для алиаса - значение остаётся родительским корнем.

Как задать корень WWW через chroot или open_basedir для изоляции PHP?

Директива open_basedir в php.ini ограничивает файлы, к которым PHP имеет доступ. Это не меняет DocumentRoot, но влияет на то, какие файлы скрипты могут читать/писать. Пример:

open_basedir = /var/www/myproject:/tmp

Такая настройка полезна для безопасности: если скрипт попытается обратиться к файлу вне указанных папок, PHP выдаст ошибку. Однако корень WWW остаётся прежним. Полноценная смена корня возможна через chroot для процесса веб-сервера, но это сложная конфигурация, выходящая за рамки статьи.

Типичные ошибки

  • Слишком строгий open_basedir может сломать работу системных библиотек.
  • Необходимо указывать все необходимые пути, включая папки для сессий и логов.

Расширенные примеры и результаты

Пример 1: Проверка значения DOCUMENT_ROOT в PHP

Создайте файл info.php с содержимым:

Пример
<?php
echo "Document Root: " . $_SERVER['DOCUMENT_ROOT'] . "\n";
echo "Script filename: " . $_SERVER['SCRIPT_FILENAME'];
?>

Результат при стандартной настройке (DocumentRoot = /var/www/html):

Document Root: /var/www/html
Script filename: /var/www/html/info.php

После изменения DocumentRoot в конфигурации на /var/www/example/public результат изменится соответствующим образом.

Пример 2: Запуск встроенного PHP-сервера с явным корнем

Пример
mkdir -p /tmp/test_php/public
cd /tmp/test_php
echo "<?php echo 'Hello from ' . \$_SERVER['DOCUMENT_ROOT']; ?>" > public/index.php
php -S localhost:8080 -t public/

Откройте браузер http://localhost:8080. Результат:

Hello from /tmp/test_php/public

Вывод показывает, что корнем стала папка public. Этот способ идеален для быстрой разработки.

Пример 3: Настройка Alias в Nginx с демонстрацией DOCUMENT_ROOT

Конфигурация Nginx:

Пример
server {
    listen 80;
    server_name example.com;
    root /var/www/main;
    location /sub/ {
        alias /var/www/sub/;
        index index.php;
        location ~ \.php$ {
            fastcgi_pass unix:/var/run/php/php8.1-fpm.sock;
            include fastcgi_params;
            fastcgi_param SCRIPT_FILENAME $request_filename;
        }
    }
}

Поместите info.php в /var/www/sub. Результат при запросе /sub/info.php:

Document Root: /var/www/main
Script filename: /var/www/sub/info.php

Обратите внимание: DOCUMENT_ROOT остаётся родительским корнем, а SCRIPT_FILENAME берётся из алиаса. Это важная особенность, которую нужно учитывать при разработке.

Пример 4: Символическая ссылка и FollowSymLinks в Apache

Создайте символическую ссылку в DocumentRoot:

Пример
sudo ln -s /home/user/other_project /var/www/html/other

В конфигурации виртуального хоста Apache должна быть опция:

Пример

    Options Indexes FollowSymLinks
    AllowOverride All
    Require all granted

Теперь запрос http://example.com/other/index.php выполнит скрипт из /home/user/other_project. Проверка DOCUMENT_ROOT:

Пример
echo $_SERVER['DOCUMENT_ROOT']; // /var/www/html

Корень не изменился, но файлы доступны. Убедитесь, что права доступа у www-data на /home/user/other_project разрешены.

Пример 5: Использование open_basedir для ограничения корня PHP

В файле /etc/php/8.1/apache2/php.ini (или fpm/php.ini) добавьте:

Пример
open_basedir = /var/www/myproject:/tmp

Перезагрузите PHP-FPM или Apache. После этого PHP-скрипты из проекта /var/www/myproject смогут обращаться только к файлам внутри этой папки и /tmp. Попытка прочитать /etc/passwd вызовет ошибку:

Warning: file_get_contents(): open_basedir restriction in effect. File(/etc/passwd) is not within the allowed path(s)

Это не меняет корень WWW, но эффективно изолирует файловые операции.

Пример 6: Настройка нескольких корней через VirtualHost (Apache) для разных проектов

Пример

    ServerName site1.com
    DocumentRoot /var/www/site1


    ServerName site2.com
    DocumentRoot /var/www/site2

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

Корень WWW в PHP - comments

En
Www root php (php)