Обработка переадресованных http-запросов::Журнал СА 12.2004
www.samag.ru
     
Поиск   
              
 www.samag.ru    Web  0 товаров , сумма 0 руб.
E-mail
Пароль  
 Запомнить меня
Регистрация | Забыли пароль?
Журнал "Системный администратор"
Журнал «БИТ»
Подписка
Архив номеров
Где купить
Наука и технологии
Авторам
Рекламодателям
Контакты
   

  Опросы
  Статьи

Событие  

В банке рассола ждет сисадмина с полей фрактал-кукумбер

Читайте впечатления о слете ДСА 2024, рассказанные волонтером и участником слета

 Читать далее...

Организация бесперебойной работы  

Бесперебойная работа ИТ-инфраструктуры в режиме 24/7 Как обеспечить ее в нынешних условиях?

Год назад ИТ-компания «Крок» провела исследование «Ключевые тренды сервисного рынка 2023». Результаты

 Читать далее...

Книжная полка  

Читайте и познавайте мир технологий!

Издательство «БХВ» продолжает радовать выпуском интересных и полезных, к тому же прекрасно

 Читать далее...

СУБД PostgreSQL  

СУБД Postgres Pro

Сертификация по новым требованиям ФСТЭК и роль администратора без доступа к данным

 Читать далее...

Критическая инфраструктура  

КИИ для оператора связи. Готовы ли компании к повышению уровня кибербезопасности?

Похоже, что провайдеры и операторы связи начали забывать о требованиях законодательства

 Читать далее...

Архитектура ПО  

Архитектурные метрики. Качество архитектуры и способность системы к эволюционированию

Обычно соответствие программного продукта требованиям мы проверяем через скоуп вполне себе понятных

 Читать далее...

Как хорошо вы это знаете  

Что вам известно о разработках компании ARinteg?

Компания ARinteg (ООО «АРинтег») – системный интегратор на российском рынке ИБ –

 Читать далее...

Графические редакторы  

Рисование абстрактных гор в стиле Paper Cut

Векторный графический редактор Inkscape – яркий представитель той прослойки open source, с

 Читать далее...

День сисадмина  

Учите матчасть! Или как стать системным администратором

Лето – время не только отпусков, но и хорошая возможность определиться с профессией

 Читать далее...

День сисадмина  

Живой айтишник – это всегда движение. Остановка смерти подобна

Наши авторы рассказывают о своем опыте и дают советы начинающим системным администраторам.

 Читать далее...

Виртуализация  

Рынок решений для виртуализации

По данным «Обзора российского рынка инфраструктурного ПО и перспектив его развития», сделанного

 Читать далее...

Книжная полка  

Как стать креативным и востребованным

Издательский дом «Питер» предлагает новинки компьютерной литературы, а также книги по бизнесу

 Читать далее...

Книжная полка  

От создания сайтов до разработки и реализации API

В издательстве «БХВ» недавно вышли книги, которые будут интересны системным администраторам, создателям

 Читать далее...

Разбор полетов  

Ошибок опыт трудный

Как часто мы легко повторяем, что не надо бояться совершать ошибки, мол,

 Читать далее...

1001 и 1 книга  
19.03.2018г.
Просмотров: 6143
Комментарии: 0
Машинное обучение с использованием библиотеки Н2О

 Читать далее...

12.03.2018г.
Просмотров: 6856
Комментарии: 0
Особенности киберпреступлений в России: инструменты нападения и защита информации

 Читать далее...

12.03.2018г.
Просмотров: 4139
Комментарии: 0
Глубокое обучение с точки зрения практика

 Читать далее...

12.03.2018г.
Просмотров: 2978
Комментарии: 0
Изучаем pandas

 Читать далее...

12.03.2018г.
Просмотров: 3781
Комментарии: 0
Программирование на языке Rust (Цветное издание)

 Читать далее...

19.12.2017г.
Просмотров: 3789
Комментарии: 0
Глубокое обучение

 Читать далее...

19.12.2017г.
Просмотров: 6283
Комментарии: 0
Анализ социальных медиа на Python

 Читать далее...

19.12.2017г.
Просмотров: 3134
Комментарии: 0
Основы блокчейна

 Читать далее...

19.12.2017г.
Просмотров: 3434
Комментарии: 0
Java 9. Полный обзор нововведений

 Читать далее...

16.02.2017г.
Просмотров: 7246
Комментарии: 0
Опоздавших не бывает, или книга о стеке

 Читать далее...

17.05.2016г.
Просмотров: 10616
Комментарии: 0
Теория вычислений для программистов

 Читать далее...

30.03.2015г.
Просмотров: 12336
Комментарии: 0
От математики к обобщенному программированию

 Читать далее...

18.02.2014г.
Просмотров: 13969
Комментарии: 0
Рецензия на книгу «Читаем Тьюринга»

 Читать далее...

13.02.2014г.
Просмотров: 9100
Комментарии: 0
Читайте, размышляйте, действуйте

 Читать далее...

12.02.2014г.
Просмотров: 7053
Комментарии: 0
Рисуем наши мысли

 Читать далее...

10.02.2014г.
Просмотров: 5362
Комментарии: 3
Страна в цифрах

 Читать далее...

18.12.2013г.
Просмотров: 4594
Комментарии: 0
Большие данные меняют нашу жизнь

 Читать далее...

18.12.2013г.
Просмотров: 3402
Комментарии: 0
Компьютерные технологии – корень зла для точки роста

 Читать далее...

04.12.2013г.
Просмотров: 3128
Комментарии: 0
Паутина в облаках

 Читать далее...

03.12.2013г.
Просмотров: 3378
Комментарии: 0
Рецензия на книгу «MongoDB в действии»

 Читать далее...

02.12.2013г.
Просмотров: 2999
Комментарии: 0
Не думай о минутах свысока

 Читать далее...

Друзья сайта  

 Обработка переадресованных http-запросов

Архив номеров / 2004 / Выпуск №12 (25) / Обработка переадресованных http-запросов

Рубрика: Веб /  Веб-технологии

АЛЕКСЕЙ МИЧУРИН

Обработка переадресованных http-запросов

Согласитесь, что адрес http://site.ru/news/page2.html намного удобнее, чем http://site.ru/cgi-bin/news/view.cgi?page=2. Первый из них гораздо легче запомнить, записать, продиктовать по телефону. В этой статье я хотел бы рассмотреть наиболее доступные приёмы перенаправления http-запросов, делая упор на способы их обработки.

Знакомство с проблемой

Когда обсуждается некая обработка запроса, конечно, подразумевается, что на сервере есть какие-то активные элементы (программы, сценарии...), способные обработать запрос и обеспечить определённую «реакцию». Программы обычно получают необходимую информацию либо со стандартного потока ввода (при запросе POST), либо из строки запроса, содержащейся в адресе справа от вопросительного знака (при запросе GET). Эти механизмы передачи данных прекрасно известны, документированы, поддержаны в неисчислимом множестве модулей и библиотек, и я не буду касаться их в настоящей статье. Я как раз хотел бы обсудить другие возможности, позволяющие передать информацию на сервер. То есть мы будем запускать сценарии, формировать веб-страницы динамически, но не будем включать в адрес ни знака вопроса, ни строку запроса. Метод POST мы тоже использовать не будем.

Как же в таком случае передать скрипту информацию? Ответ прост: через адрес. То есть мы рассмотрим приёмы, позволяющие вызвать один и тот же скрипт, используя разные адреса; а также обсудим, как скрипт может получить информацию о том, по какому адресу он был вызван на этот раз. Обсудим, какие дополнительные возможности обеспечивает такой способ управления скриптами.

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

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

Несколько слов о файле .htaccess

Файл .htaccess – это просто текстовый файл, который размещается в одной директории с веб-документами или сценариями. То есть для его редактирования вполне достаточно полномочий, позволяющих управлять содержимым сервера, коими обладают все владельцы виртуальных серверов. В нём хранятся конфигурационные директивы для сервера. Действие этих директив распространяется на все файлы, принадлежащие директории, в которой расположен .htaccess. Оно распространяется и на файлы всех вложенных директорий, хотя вложенные директории могут, в свою очередь, тоже содержать файлы .htaccess, которые переопределят настройки, данные в родительских директориях.

Вообще говоря, использование имени .htaccess совсем не обязательно. Ваш сервер может быть настроен на использование другого имени вместо .htaccess. Настройка производится инструкцией:

AccessFileName имя_файла

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

Какие настройки можно производить в .htaccess? Ответ зависит от нравов администратора. Все конфигурационные инструкции Apache, допустимые в .htaccess, поделены на категории. Администратор обычно даёт пользователю только часть полномочий, разрешая ему изменять настройки, принадлежащие только к определённым категориям. Настройка этих ограничений производится инструкцией:

AllowOverride список_категорий_или_All_или_None

Поэтому прежде чем писать свой .htaccess, осведомитесь у администратора сервера, какие категории настроек вам доступны.

Существует всего пять категорий:

  • AuthConfig – директивы, отвечающие за организацию авторизованного доступа;
  • FileInfo – директивы, управляющие обработкой ошибок и отвечающие за информацию о языках и кодировках и прочее;
  • Indexes – команды, отвечающие за доступ к директориям, то есть за те случаи, когда файл в адресе не указан;
  • Limit – команды, позволяющие ограничить доступ к ресурсу, например, закрыть или открыть доступ для клиентов, имеющих определённые IP-адреса;
  • Options – всего две инструкции Options и XBitHack; первая регламентирует работу механизмов CGI, SSI и автоматического составления листинга директорий; вторая управляет реакцией SSI-процессора на атрибут файла «исполняемый» и используется весьма редко.

Перейдём теперь к приёмам обработки адреса. Естественно, чтобы передать скрипту информацию через адрес, мы должны иметь возможность вызвать один и тот же скрипт, используя разные адреса. Когда это происходит?

Директива DirectoryIndex

Начнём наш экскурс с самой простой возможности, о которой знают практически все. Директива DirectoryIndex принадлежит к категории Indexes и служит для определения файлов, выступающих в роли традиционного index.html.

Если .htaccess, расположенный в некоторой директории, содержит инструкцию:

DirectoryIndex index.html /cgi-bin/index.cgi

то при обращении к этой директории (без указания файла) сервер действует по следующему алгоритму: сперва он будет искать файл index.html, если таковой существует, то будет выдан клиенту, в противном случае, сервер выдаст результат выполнения сценария /cgi-bin/index.cgi. Если и последний не существует, то клиент получит сообщение об ошибке 404.

Если разместить такой .htaccess сразу в двух директориях /one/и /two/, то и по адресу /one/, и по адресу /two/клиент получит результат работы /cgi-bin/index.cgi (естественно, если соответствующий index.html не найден). Мы вызываем один и тот же скрипт по разным адресам. Для получения такого эффекта может быть достаточно и одного подобного .htaccess. В нашем случае и для директории /one/first/, и /one/second/в отсутствии index.html будет вызван /cgi-bin/index.cgi.

Для нас существенно то, что сценарий /cgi-bin/index.cgi, кроме обычных переменных окружения, получит две дополнительные: REDIRECT_URL и REDIRECT_STATUS. Первая будет содержать запрошенный адрес без имени сервера. Вторая – статус (обычно 200). То есть сценарий может «определить», для какой директории он вызван, и совершить адекватные действия. Например, для одних директорий (скажем, с html-документами) он может составлять индекс, придавая ему должный вид и включая в него только определённые файлы, а для других директорий (допустим, с графикой) он будет перенаправлять пользователя на первую страницу или выдавать сообщение об ошибке.

Для полноты картины осталось только сказать о переменной REDIRECT_QUERY_STRING: она практически эквивалентна QUERY_STRING (о которой мы договорились не упоминать в этой статье). Если в директории /paper сервера paper.ru в файле .htaccess находится инструкция:

DirectoryIndex /cgi-bin/index.cgi

то при запросе адреса http://paper.ru/paper?string=data или http://paper.ru/paper/?string=data, как вы уже догадались, будет вызван сценарий /cgi-bin/index.cgi, но наряду с переменной QUERY_STRING ему будет передана ещё и REDIRECT_QUERY_STRING. Обе они будут равны строке запроса, в нашем примере string=data. Разница между этими переменными состоит только в том, что когда строка запроса отсутствует, переменная QUERY_STRING существует, но равна пустой строке, а REDIRECT_QUERY_STRING не существует вовсе.

Обработка ошибок. Директива ErrorDocument

Директива ErrorDocument принадлежит к категории FileInfo и предназначена для определения файлов, выдаваемых клиенту, если обработка запроса вызвала ошибку.

Если добавить в .htaccess инструкцию:

ErrorDocument 404 /cgi-bin/error.cgi

то при возникновении ошибки 404 будет выполнен сценарий /cgi-bin/error.cgi. Ему будут переданы четыре дополнительные переменные:

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

Кроме того, при наличии строки запроса создаётся переменная REDIRECT_QUERY_STRING, описанная выше.

Эти переменные удобно использовать не только в CGI-сценариях, но в SSI-документах. Так, если создать .htaccess с директивой:

ErrorDocument 404 /error/404.shtml

а в файле /error/404.shtml разместить следующий SSI-код:

<html>

<head><title>404</title></head>

<body>

<h1>Файл не найден!</h1>

Файл <b><!--#echo var="REDIRECT_URL" --></b> был запрошен

методом <b><!--#echo var="REDIRECT_REQUEST_METHOD" --></b>.

Запрос был перенаправлен на этот документ со статусом

<b><!--#echo var="REDIRECT_STATUS" --></b>. Полная диагностика

такова: <b><!--#echo var="REDIRECT_ERROR_NOTES" --></b>.

(все использованные переменные доступны и в CGI)

</body>

</html>

 то при обращении к несуществующему файлу /is_it_is.html клиент получит следующее сообщение:

Рисунок 1

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

ErrorDocument 404 "Sorry. File not found

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

Обратите внимание, закрывающей кавычки в указанной директиве нет.

Авторизованный доступ

Прежде всего, скажу несколько слов о том, как активизировать механизм авторизации. Чтобы ограничить доступ к некоторой директории (и ко всем вложенным директориям), следует написать в .htaccess приблизительно такие инструкции:

AuthType Basic

AuthName "By Invitation Only"

AuthUserFile /home/www/paper/secret/passwd

Require valid-user

Все они, как вы, наверное, догадались, принадлежат к категории AuthConfig.

Первая из них задаёт тип процедуры авторизации, на практике используется только Basic.

Вторая инструкция задаёт текст, который отобразит браузер в окне диалога.

Рисунок 2

Директива AuthUserFile определяет файл с паролями пользователей, который легко создать с помощью утилиты htpasswd, входящей в поставку Apache. Обратите внимание, файл паролей в целях безопасности можно (и желательно!) размещать вне дерева директорий, доступных через Web.

Директива Require регламентирует, какие пользователи или группы пользователей имеют доступ к данному ресурсу. В приведённом примере я позволил всем пользователям (конечно, только если они пройдут процедуру авторизации) обращаться к файлам и подкаталогам директории, где размещён наш .htaccess.

Техника ограничения доступа описана многократно, и я не хотел бы повторять здесь других авторов. Для нас будет важно то, что когда клиент работает в директории авторизованно, сервер создаёт ещё две дополнительные переменные: REMOTE_USER и AUTH_TYPE. Первая, как вы понимаете, содержит имя пользователя, вторая – тип авторизации (Basic).

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

Эти переменные доступны и CGI-сценариям, и SSI-документам. Например, страница enter.shtml:

<html>

<head><title>Enter</title></head>

<body>

<h1>Hi, <!--#echo var="REMOTE_USER" -->!</h1>

<p>(AUTH_TYPE=<!--#echo var="AUTH_TYPE" -->)</p>

</body>

</html>

Будет выглядеть так:

Рисунок 3

После успешной авторизации переменные REMOTE_USER и AUTH_TYPE передаются и обработчикам ошибок в дополнение ко всем перечисленным выше, содержащим информацию об ошибке. Эта передача происходит даже в том случае, если обработчик находится за пределами засекреченной области (ошибка, конечно, должна произойти в засекреченной области).

При неудачной авторизации возникает ошибка 401, для которой тоже может быть назначен обработчик:

ErrorDocument 401 /error/401.shtml

или

ErrorDocument 401 /cgi-bin/error.cgi

Мне осталось только заметить, что пользователи могут быть объединены в группы. Для этого существует директива AuthGroupFile. Так вот, информация о том, к какой группе принадлежит пользователь, не передаётся сценарию.

Применение PATH_INFO

Сервер Apache (и не только он) предоставляет интересную возможность: если существует сценарий /cgi-bin/script.cgi, то любой адрес вида /cgi-bin/script.cgi/location/doc.ext считается вполне допустимым. При его обработке выполняется сценарий /cgi-bin/script.cgi, а строка /location/doc.ext передаётся ему в переменной PATH_INFO. Кроме неё, создаётся переменная PATH_TRANSLATED, содержащая как бы путь к запрашиваемому файлу относительно корня файловой системы сервера. Если в нашем примере предположить, что документы сервера расположены в директории /www/docs, то PATH_TRANSLATED будет содержать путь /www/docs/location/doc.ext.

Путь, который был на самом деле запрошен клиентом, как обычно, доступен через переменную REQUEST_URI.

Эта возможность находит самые разные применения. Например, вы можете хранить все документы в кодировке КОИ-8, и их CP-1251-модификации создавать «на лету», используя виртуальные пути вида /cgi-bin/koi2win.cgi/... Единственное, что может доставить вам хлопоты – для реализации такого подхода потребуется все перекрёстные ссылки в документах делать относительными, а все адреса графических и мультимедийных объектов, CSS-, JS-компонент делать абсолютными. В противном случае вам придётся сделать сценарий koi2win.cgi чуть умнее, чем просто перекодировщик: он должен будет правильно (без искажений) передавать файлы, не являющиеся HTML-документами и не требующие перекодировки, что, впрочем, не так уж сложно реализовать.

Другое применение – хранение в виртуальном пути некой информации (например, идентификатора сессии). Это очень удобно. Для сценария, выполняемого на сервере, виртуальный путь принципиально ничем не отличается от строки запроса. Браузер же рассматривает его просто как путь, нисколько не ощущая его виртуальности. Следуя по относительным ссылкам, браузер сохраняет путь (или его часть).

Пример такого сценария я и хочу привести:

#!/usr/bin/perl

use strict;

my ($path, $script) = @ENV{qw/PATH_INFO SCRIPT_NAME/};

my ($color, $file) = $path=~m|/([^/]+)/([^/]+)$|;

my $html_list='';

foreach (1..5) {

    $html_list .= <<"TEXT";

<li><a href="$_.html">$_.html</a></li>

TEXT

}

print <<"TEXT";

Content-Type: text/html

<html>

<head><title>$script</title></head>

<body text="$color" bgcolor="white"

 link="$color" vlink="$color">

<h1>$file</h1>

<ul>$html_list</ul>

</body>

</html>

TEXT

Как видите, сценарий выделяет из строки PATH_INFO (сохранённой в переменной $path) два последние элемента пути. Первая из этих частей интерпретируется как цвет (сохраняется в переменой $color), вторая – как имя файла (переменная $file), её можно было бы использовать для подключения определённого содержания.

В цикле foreach мы создаём небольшое навигационное меню с относительными ссылками.

Разместим наш сценарий по адресу: /cgi-bin/pi.cgi.

Теперь по адресу /cgi-bin/pi.cgi/gray/3.html мы увидим:

Рисунок 4

Код страницы таков:

<html>

<head><title>/cgi-bin/pi.cgi</title></head>

<body text="gray" bgcolor="white"

 link="gray" vlink="gray">

<h1>3.html</h1>

<ul><li><a href="1.html">1.html</a></li>

<li><a href="2.html">2.html</a></li>

<li><a href="3.html">3.html</a></li>

<li><a href="4.html">4.html</a></li>

<li><a href="5.html">5.html</a></li>

</ul>

</body>

</html>

Как видите, все ссылки «указывают» тоже на серые документы, вернее, они оставляют информацию о цвете (путь) неизменной.

По адресу /cgi-bin/pi.cgi/red/1.html мы обнаружим аналогичную структуру «красных документов».

Мысль, намеченную в этом сценарии, легко развить в необходимом русле. Единственное, о чем следует позаботиться – это безопасность. Отсутствие хотя бы каких-нибудь проверок в сценарии pi.cgi чревато только комичными ситуациями. Например, такой: /cgi-bin/pi.cgi/white/1.html. Но если ваш сценарий работает с файлами, то всегда надо быть готовым к тому, что кто-то запросит документ /cgi-bin/koi2win.cgi/../../../etc/passwd. Конечно, конкретно эта атака наивна и, скорее всего, не представляет серьёзной опасности, хотя всё зависит от того, как устроен koi2win.cgi.

Замечу ещё, что всё сказанное справедливо не только для CGI-сценариев, но и для SSI-документов. При обращении к ресурсу /dir/doc.shtml/data (конечно, предполагается, что doc.shtml не директория, а SSI-документ) будут также созданы две дополнительные переменные PATH_INFO и PATH_TRANSLATED.

Кроме того, SSI-процессором всегда создаётся переменная DOCUMENT_PATH_INFO, которая пуста, если PATH_INFO и PATH_TRANSLATED отсутствуют.

Я думаю, что у внимательного читателя уже возник вопрос, можно ли усовершенствовать наше решение так, чтобы избежать таких «неповоротливых» адресов, превратив, например, /cgi-bin/pi.cgi/gray/3.html в /color/gray/3.html. Ответ на этот вопрос – да, возможно. Как раз это обсуждается в следующем разделе.

Магия Action

Наверное, самые большие возможности предоставляет директива Action. С её помощью вы можете назначить скрипт-обработчик для определённых типов файлов.

Приведу пример. Напишем в .htaccess следующие директивы:

AddHandler my-handler .para

Action my-handler /cgi-bin/para.cgi

Обе директивы, содержащиеся в этом файле, принадлежат к категории FileInfo.

Первая – добавляет новый дескриптор файла, ассоциированный с расширением .para. Теперь все файлы *.para будут ассоциироваться с манипулятором my-handler. Особенностью директивы AddHandler является то, что она не чувствительна к регистру, то есть распространяется в равной мере и на файлы *.Para, *.PARA, *.PaRa и так далее. Кроме того, символ «точка» необязателен.

Вторая директива – Action – назначает действие, которое необходимо выполнять для файлов, ассоциированных с манипулятором my-handler. Теперь любое обращение к файлу *.para должно приводить к запуску сценария /cgi-bin/para.cgi.

Для полноты картины добавлю, что вместо дескриптора можно использовать MIME-тип. В принципе, нетрудно представить случаи, когда это будет удобно. Например, вы поддерживаете публичный хостинг и хотите, чтобы ко всем страницам ваших клиентов автоматически добавлялся баннер. Тогда проще привязать обработчик html-документов не к двум расширениям (.html и .htm), а к одному-единственному MIME-типу (text/html).

С содержимым .htaccess разобрались, давайте теперь рассмотрим /cgi-bin/para.cgi.

Если разместить наш .htaccess в директории /action, то при обработке адреса /action/1.para будет выполнен сценарий /cgi-bin/para.cgi, которому будет передан целый ряд дополнительных переменных:

  • PATH_INFO – содержит адрес запрошенной «страницы», в нашем случае это /action/1.para;
  • PATH_TRANSLATED – полное имя запрошенного файла, например, /www/docs/action/1.para;
  • REDIRECT_STATUS – если всё в порядке, то 200. Обратите внимание: если файл 1.para не существует, то код всё равно будет 200. То есть сервер успешно запустил скрипт /cgi-bin/para.cgi, а существует ли файл 1.para – проблема скрипта.
  • REDIRECT_URL – равно PATH_INFO.

Если в адресе содержалась ещё и строка запроса (например, /action/1.para?subsection=3), то она не включается в PATH_INFO и REDIRECT_URL, а попадает в переменные QUERY_STRING и REDIRECT_QUERY_STRING, о которых уже говорилось в начале статьи. Если вам понадобится полный адрес (вместе со строкой запроса), то ищите его, как обычно, в переменной REQUEST_URI.

Давайте разберём простенький пример. Пусть в файлах *.para будет храниться просто ASCII-текст, а скрипт /cgi-bin/para.cgi будет формировать html-документы из ASCII-текста, производя с ним нехитрые преобразования: квотирование небезопасных символов (&, «, >, <), добавление тега
в конце каждой строки, добавление тегов, открывающих и закрывающих html-документ. Имя файла, который следует обработать, сценарий будет брать из переменной PATH_TRANSLATED. Код сценария таков:

#!/usr/bin/perl

use strict;

my ($file, $url)=@ENV{qw/PATH_TRANSLATED REDIRECT_URL/};

open FH, "<$file" or die;

my $f=join('', <FH>);

close FH;

$f=~s/\&/&amp;/g;

$f=~s/\</&lt;/g;

$f=~s/\>/&gt;/g;

$f=~s/\"/&quot;/g;

$f=~s/\n/<br>\n/g;

print <<"TEXT";

Content-Type: text/html

<html>

<head>

<title>$url</title>

</head>

<body><h1>$url</h1>

$f

</body>

</html>

TEXT

Теперь, если в файле /action/1.para находится следующие три строки:

"AAA"

<BBB>

CCC

то по адресу /action/1.para браузер обнаружит результат работы нашего скрипта:

<html>

<head>

<title>/action/1.para</title>

</head>

<body><h1>/action/1.para</h1>

&quot;AAA&quot;<br>

&lt;BBB&gt;<br>

CCC

</body>

</html>

Выглядеть он будет так:

Рисунок 5

Как видите, текст корректно преобразован в HTML-документ.

Вы, наверное, уже обратили внимание на то, что описанный подход очень похож на подход предыдущего раздела. Действительно, по адресу /cgi-bin/para.cgi/action/1.para мы увидим почти то же самое. «Почти» потому, что в этом случае переменной REDIRECT_URL уже не будет. Если бы мы использовали вместо неё PATH_INFO, то скрипт вообще «не почувствовал» бы разницы, будь он вызван как /cgi-bin/para.cgi/action/1.para или как /action/1.para.

Но самое интересное – сходства этих двух подходов на этом не заканчиваются. Оказывается, что и при Action-подходе сервер не проверяет, существует ли файл на самом деле! При обращении к любому файлу с расширением .para (в директории /action), независимо от того, существует ли файл, вызывается скрипт /cgi-bin/para.cgi. Даже REDIRECT_STATUS сохраняет значение 200. То есть все замечания относительно безопасности остаются в силе.

А теперь вопрос «на засыпку»: как отреагирует сервер на запросы /action/dir/1.para, /action/dir.para/1.para, /action/dir.para/1.text?

Естественно, ни директории /action/dir, ни директории /action/dir.para не существует.

Правильный ответ таков: в первом случае возникнет ошибка 404. Её бы не возникло, если бы /action/dir существовала, даже в том случае, если сам файл /action/dir/1.para отсутствовал. Во втором и третьем случаях будет как ни в чем не бывало вызван скрипт /cgi-bin/para.cgi.

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

Например, мы можем создать директорию /color и разместить в ней .htaccess со следующей директивой:

Action text/html /cgi-bin/pi.cgi

Кстати, обратите внимание, в этом примере мы обошлись без директивы AddHandler, так как обработчик привязан к определённому MIME-типу.

Теперь мы можем запустить pi.cgi двумя способами.

Первый – создать в директории /color директории, соответствующие необходимым цветам, скажем gray и green. Теперь по адресу /color/green/1.html мы обнаружим систему «зелёных» документов.

Обратите внимание: если директория /color/cyan не существует, то запрос документа /color/cyan/1.html вызовет ошибку 404.

Второй способ (внимание! это может быть потенциальная дыра в системе безопасности) – обратиться по адресу /color/hole.html/cyan/1.html. При этом директория hole.html не должна существовать. Теперь наличие расширения .html у директории hole.html приведёт к запуску pi.cgi, а он будет рассматривать только последние две компоненты пути – cyan и 1.html. Таким образом всё сработает «как часы». Так можно получить документ любого цвета, если на сервере не выполняется никаких проверок (как это сделано в нашем беспечном pi.cgi).

И снова обращаю ваше внимание на то, что если директория /color/hole.html существует, а /color/hole.html/cyan не существует, то по адресу /color/hole.html/cyan/1.html мы получим ошибку 404.

Ограничения

Вы видите, что сценарий или скрипт можно запустить не только «напрямую» (как /cgi-bin/forum.cgi), но и многими другими вполне доступными способами. И кроме традиционно используемой переменной QUERY_STRING сервер создаёт множество полезных переменных, но не забывайте, что использовать их надо не менее осторожно, чем QUERY_STRING.

Даже мои небольшие примеры не лишены изъянов. Так, я довольно опрометчиво встраиваю в HTML-код, создаваемый SSI-процессором, такие переменные, как PATH_INFO. Подобные переменные задаются удалённым пользователем. Не исключено, что он сформирует такой адрес, по которому будет выдаваться HTML-документ, оснащённый вредоносным JavaScript-кодом или иным аппаратом (иногда для осуществления атаки оказывается достаточно считаных байт). Таким образом злоумышленник может скомбинировать адрес, наделяющий ваш ресурс вредоносными свойствами. Никогда нельзя использовать напрямую переменные, значение которых определяется удалённо.

Следует отметить, что описанный подход, будучи реализован в чистом виде, практически полностью исключает возможность обработки форм. Это большой минус, но ни один из перечисленных приёмов не лишает вас возможности использовать переменную QUERY_STRING или REDIRECT_QUERY_STRING и обрабатывать формы, отправленные методом GET. Также к любому сценарию можно обратиться методом POST. Но самое главное, существует широкий круг задач, ограничивающихся организацией навигации и не предполагающих работу с формами (от лент новостей и фото-галерей до веб-каталогов). Именно в этих случаях наиболее оправданно применение подходов, описанных в настоящей статье.


Комментарии отсутствуют

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

Комментарии могут оставлять только зарегистрированные пользователи

               Copyright © Системный администратор

Яндекс.Метрика
Tel.: (499) 277-12-45
E-mail: sa@samag.ru