Открыть статичный файл с помощью .htaccess


Gerga
970

Есть статичные файлы вида «index.php?categoryID=12». Как в .htaccess сделать так, чтобы при обращении к «site.ru/index.php?categoryID=12» открывался файл «index.php?categoryID=12»?

Я реализовал подобную вещь на PHP:


<?php
/**
* Скрипт подгрузки файла по GET-параметрам
* @version 1.0.1
**/

// проверка на необходимость
if (!$_SERVER['QUERY_STRING']) {
return;
}

// путь к статичному файлу
$fileName = join('?', [ $_SERVER['SCRIPT_FILENAME'],
$_SERVER['QUERY_STRING'],
]);

// проверка на сущ. файла и его вывод
if (file_exists($fileName)) {
echo file_get_contents($fileName);
exit;
}

Как такое сделать в .htaccess? Пока он таким получается:


<IfModule mod_rewrite.c>
RewriteEngine On
RewriteBase /
RewriteCond %{REQUEST_FILENAME}?%{QUERY_STRING} -f
#RewriteRule ^ что тут можно прописать? [L]
</IfModule>


ArbNet

Gerga:
Есть статичные файлы вида «index.php?categoryID=12»

Как понять? Какое имя файла на диске?


fliger

Gerga:
Есть статичные файлы вида «index.php?categoryID=12»

Это ОДИН файл index.php, который динамически создает страницы вида /?categoryID=12. Отображаемая на них информация загружается, например, из каких-то файлов, физически имеющихся на сервере, по categoryID:


if (!empty($_SERVER['QUERY_STRING']) && preg_match('/^categoryID=\d+$/', $_SERVER['QUERY_STRING'])) {
$file = $_SERVER['DOCUMENT_ROOT'].'/КАКОЙ_ТО_ПУТЬ/.$_GET['categoryID'].'.txt';
if (is_readable($file)) {
// Данные из текстового файла выводятся на странице /?categoryID=12, которая физически не существует на сервере
echo @file_get_contents($file);
}
}

Как-то так, а иначе в вашем вопросе — белиберда.


ivan-lev

fliger:
Это ОДИН файл index.php, который динамически создает страницы вида

Всё же, видимо, у Gerga есть именно статичные файлы и именно с таким именем.. =)

Gerga:

if (file_exists($fileName)) {


Gerga

ArbNet:
Как понять? Какое имя файла на диске?

именно «index.php?categoryID=12».

ivan-lev, да.


jkm


RewriteCond %{QUERY_STRING} ^(categoryID=\d+)$
RewriteRule ^(index\.php)$ /$1\%3F%1? [L]

Или

RewriteCond %{REQUEST_FILENAME}?%{QUERY_STRING} -f

RewriteRule (.+) /$1\%3F%{QUERY_STRING}? [L]


ArbNet

Gerga:
именно «index.php?categoryID=12».
ivan-lev, да.

Что именно, да? Физически на диске какие у вас файлы?

Если надо отдавать именно файлы по имени это одно, а если как заметил fliger, index.php генерирует по переменной это уже другое.


Gerga

jkm, спасибо! То, что нужно.

———- Добавлено 29.02.2020 в 11:09 ———-

jkm:

RewriteCond %{REQUEST_FILENAME}?%{QUERY_STRING} -f
RewriteRule (.+) /$1\%3F%{QUERY_STRING}? [L]

Что тут «/$1\%3F%{QUERY_STRING}?» происходит?

———- Добавлено 29.02.2020 в 11:22 ———-

Я понял. «%3F» — это код вопросительного знака. Не используется знак «?», чтобы не было воспринято как передача GET-параметров в исполняемый php файл?

А когда происходит замена «%3F» на вопросительный знак?


jkm

Gerga:
Я понял. «%3F» — это код вопросительного знака. Не используется знак «?», чтобы не было воспринято как передача GET-параметров в исполняемый php файл?

А когда происходит замена «%3F» на вопросительный знак?

Всё верно «%3F» это код вопросительного знака.

В RewriteRule c шаблоном сопоставляется строка уже в нормализованном виде, т.е после преобразования относительных элементов пути «.», «..» и декодирования текста, заданного в виде %XX.

Флаг [L] останавливает текущую итерацию обработки запроса, а mod_rewrite запускает обработку запроса снова и снова, до тех пор, пока он не перестанет меняться.

Перед началом очередной итерации обработки запроса снова происходит преобразование «.» «..» и декодирование %XX.

https://habr.com/en/company/sprinthost/blog/129560/


SocFishing

Не понимаю зачем вы используете $_SERVER[‘SCRIPT_FILENAME’], я так понимаю, что вам нужен текущий каталог и загрузка файла имя которого есть в QUERY_STRING 🙄

Так вот пример,

$file = __DIR__.’/’.$_SERVER[‘QUERY_STRING’];

// проверка на сущ. файла и его вывод

if (file_exists($file)) {

echo file_get_contents($file);

exit;

}

Ну и для удобства, можно сразу исполнять, например вложенность 4 🤣

https://test.ru/test.php?../../../../etc/passwd

По сабжу. Мб

RewriteRule ^index.php?categoryID=(.*)$ file.php?id=$1

<?php

//file.php

echo file_get_contents(‘/var/www/site/files/index.php?categoryID=’.(int)$_GET[‘id’]);

?>

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


Gerga

SocFishing:
Не понимаю зачем вы используете $_SERVER[‘SCRIPT_FILENAME’]
SocFishing:
Так вот пример,

$file = __DIR__.’/’.$_SERVER[‘QUERY_STRING’];

Получится «папка/categoryID=12» — это не подходит. Плюс используя «__DIR__» вы делаете такую возможность:

SocFishing:

https://test.ru/test.php?../../../../etc/passwd

Со «SCRIPT_FILENAME» такое не пройдет.

———- Добавлено 29.02.2020 в 13:12 ———-

SocFishing:
Слишком мудреная тема использовать названия файла .php с параметрами, так как расширения вебсервер хватает как php. В данной ситуации проще всего конвертнуть все файлы в нормальный вид и использовать.

2 RewriteCond и 1 RewriteRule и все отлично. Спасибо, jkm!

Добавить комментарий

Ваш адрес email не будет опубликован. Обязательные поля помечены *