Быстрая CMS
Обратная связь Карта сайта
Главная Создание сайтов Практика Строим CMS Наивное О проекте Блог

Проверка корректности запроса

Все основные функции движка уже готовы. Во всяком случае, те, что отвечают за выборку контента и навигацию. Осталась одна деликатная тема: что делать, если кто-то запросил некорректный URL?

Статические сайты обслуживаются сервером – если запрошенный файл не найден, сервер выдаст заголовок (HTTP Response Header) с кодом статуса «404 Not Found». Но в случае динамического движка отдаваемый документ определяется не по имени файла в URL, а по переданным скрипту параметрам. При неверных параметрах файл скрипта все равно лежит на своем месте, значит сервер запустит его и отдаст код статуса «200 OK». А документа, соответствующего параметрам, нет. Поэтому скрипт должен определить некорректные парамеры и переписать код статуса до начала выдачи документа. И прекратить работу, не пытаясь искать несуществующие данные.

Для такого аварийного завершения нам потребуются всего две вещи. Первая – HTML-файл страницы с сообщением об ошибке – для выдачи в браузер пользователя. Приготовим его заранее и положим в корневую директорию сайта под именем 404.htm (так он у нас прописан в файле конфигурации).
Вторая – функция, которая отсылает HTTP-заголовок с кодом ошибки и прекращает работу скрипта. Выглядит она так:


<?php
function err404($pageout=FALSE) {
global $charset,$page404;
  header("Cache-Control: no-cache, no-store");
  header("Content-Type: text/html; charset=".$charset);
  header($_SERVER['SERVER_PROTOCOL']." 404 Not Found");
  if ($pageout) readfile('./'.$page404);
  exit();
}
?>

Глобальные переменные $charset и $page404 определены в файле конфигурации. А параметр $pageout – логическая переменная, определяющая, выдавать страницу с сообщением об ошибке или нет. По умолчанию его значение FALSE – то есть функция только отдаст HTTP-заголовок с кодом статуса и прекратит работу. Версия протокола HTTP берется из переменной окружения SERVER_PROTOCOL, чтобы послать отклик именно с той версией, по которой работает сервер. Если функцию запустить с параметром TRUE, то после передачи заголовка она считает и отправит в поток вывода файл со страницей сообщения. Выдача только заголовка без сообщения может пригодиться в дальнейшем – в тех случаях, когда точно известно, что запрос послан не браузером, а роботом.

В директории /libs создаем файл functn.inc.php – в него помещаем функцию err404() и функцию hierarchy(), описанную в разделе Разбор структуры сайта. В тот же файл записываем функции выборки разделов для меню: getmain(), getsub() и getlevel(), описанные в разделе Выборка разделов для меню. Базовая библиотека готова. Теперь самое время провести проверку корректности запроса. Этот код уже пойдет в начало центрального скрипта main.php


<?php
require('libs/start.inc.php');
require('libs/functn.inc.php');
$fakelink=FALSE;

// 1. Проверка отсутствия параметров в статическом URL
if (!empty($_urlmode) &&
    $_urlmode!='none' &&
    strpos($_SERVER['REQUEST_URI'],'?') !== FALSE)
 {
  $fakelink=TRUE;
 }

// 2. Разбор и проверка GET-параметров
if (!empty($_GET)) {
  foreach ($_GET as $key=>$val) {
    if (in_array($key,$get_arr)) $$key=trim($val);
    else {
      $fakelink=TRUE;
      break;
    }
  }
} elseif (!empty($_SERVER['QUERY_STRING'])) {
  $fakelink=TRUE;
} else $id='/';

// Если URL некорректен, посылаем 404 Not Found
if ($fakelink) err404(TRUE);

// Считываем в массив файл структуры
$h_arr=file($datapath.'struct.dat');

// Разбираем структуру сайта
$hier=hierarchy($h_arr);

// Уничтожаем массив с неразобранным файлом структуры – он больше не нужен
unset($h_arr);

// 3. Проверка наличия запрошенного раздела. Если такого нет, посылаем 404
if (!array_key_exists($id,$hier)) {
  err404(TRUE);
}
?>

В первых двух строках подгружается файл конфигурации и файл с функциями. Затем определяем логическую переменную $fakelink – она работает «флажком», который будет поднят при любом некорректном состоянии URL. Далее начинаем серию проверок.

Первое условие проводит проверку в случае, когда включен режим трансляции статических URL (переменная $urlmode не пустая и не равна 'none'). Из переменной окружения REQUEST_URI берется первоначально запрошенный (не транслированный) URL и проверяется на отсутствие вопросительного знака. Если ссылки статические, его там быть не должно – статические URL параметров не имеют.

Второе условие:

После первых двух проверок нужно остановить работу скрипта, если запрошенный URL некорректен. Что мы и делаем – при поднятом флажке $fakelink запускается передача статуса «404 Not Found» с завершением работы скрипта.

Далее, если URL корректного формата, считывается структура сайта и формируется массив разделов. И тут же следует третья проверка – если в массиве разделов не обнаружен алиас запрошенного раздела, значит пришел запрос с корректным форматом, но запрошенная страница не существует. В этом случае также выдается статус 404 и скрипт завершает работу.

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