Система управления «Сайт PRO»
Версия 20240107

Класс Request

Объект $Request: Cms\Root\Main\Request наследует Cms\Site\Base

Объект для обработки HTTP-запроса и ответа на него

Объект $Request

Исходный код
class Request extends \Cms\Site\Base { … }

Свойства

$status

$Request->status = "200 OK";

HTTP-статус ответа

Исходный код
    var $status = "200 OK";

$status_header

$Request->status_header = "HTTP/1.1 200 OK";

Заголовок HTTP-статуса ответа

Исходный код
    var $status_header = "HTTP/1.1 200 OK";

$header

$Request->header = array();

HTTP-заголовки для отправки клиенту

Исходный код
    var $header = array();

$cookie

$Request->cookie = array();

COOKIE для отправки клиенту

Исходный код
    var $cookie = array();

$extensions

$Request->extensions = array( ".html" );

Какие суффиксы в ссылках не нужно учитывать

Исходный код
    var $extensions = array( ".html" );

$default_extension

$Request->default_extension = ".html";

Суффикс в ссылке по умолчанию

Исходный код
    var $default_extension = ".html";

Методы

_GET()

$Request->_GET($key, $default=null);
Исходный код
    function _GET($key, $default = null) {
        return isset($_GET[$key]) ? $_GET[$key] : $default;
    }

_POST()

$Request->_POST($key, $default=null);
Исходный код
    function _POST($key, $default = null) {
        return isset($_POST[$key]) ? $_POST[$key] : $default;
    }

_COOKIE()

$Request->_COOKIE($key, $default=null);
Исходный код
    function _COOKIE($key, $default = null) {
        return isset($_COOKIE[$key]) ? $_COOKIE[$key] : $default;
    }

_REQUEST()

$Request->_REQUEST($key, $default=null);
Исходный код
    function _REQUEST($key, $default = null) {
        return isset($_REQUEST[$key]) ? $_REQUEST[$key] : $default;
    }

_SESSION()

$Request->_SESSION($key, $default=null);
Исходный код
    function _SESSION($key, $default = null) {
        return isset($_SESSION[$key]) ? $_SESSION[$key] : $default;
    }

init()

$Request->init();

Инициализация

Возвращает: true; null

  • Исправляет $_GET, $_POST, $_COOKIE при использовании Magic Quotes
  • Формирует $_REQUEST из $_GET, $_POST
  • Открывает буфер вывода
Исходный код
    function init() {
        # Повторный вызов
        if ($this->_init_request) return;

        # login, e-mail
        foreach (array( "login", "email", "admin_login", "admin_email" ) as $key) {
            if (isset($_GET[$key]) && is_string($_GET[$key])) $_GET[$key] = mb_strtolower($_GET[$key]);
            if (isset($_POST[$key]) && is_string($_POST[$key])) $_POST[$key] = mb_strtolower($_POST[$key]);
            if (isset($_COOKIE[$key]) && is_string($_COOKIE[$key])) $_COOKIE[$key] = mb_strtolower($_COOKIE[$key]);
        }

        # Глобальные переменные
        $this->initRequest($_COOKIE);
        $_REQUEST = array();
        $this->initRequest($_GET);
        $this->initRequest($_POST);

        # Буфер вывода
        $this->ob_status = ob_get_status();
        ob_start();

        return $this->_init_request = true;
    }

initRequest()

$Request->initRequest(&$a, $top=true);

Исправление массива

Параметры:

ИмяОписание
$a

массив

$top

массив является одним из глобальных массивов $_GET, $_POST, $_COOKIE

Возвращает: null

  • Исправляет элементы массивов $_GET, $_POST, $_COOKIE при использовании Magic Quotes
  • Добавляет элементы в $_REQUEST из $_GET, $_POST
Исходный код
    function initRequest(&$a, $top = true) {
        if (function_exists('get_magic_quotes_gpc') && get_magic_quotes_gpc()) {
            foreach ($a as $k => $v) {
                if (is_string($v)) {
                    $a[$k] = stripslashes($v);
                } elseif (is_array($v)) {
                    $this->initRequest($a[$k], false);
                }
                if ($top) $_REQUEST[$k] = $a[$k];
            }
        } else {
            foreach ($a as $k => $v) {
                if (is_string($v)) {
                    $a[$k] = $v;
                } elseif (is_array($v)) {
                    $this->initRequest($a[$k], false);
                }
                if ($top) $_REQUEST[$k] = $a[$k];
            }
        }
    }

send()

$Request->send($output=null);

Отправляет результат клиенту

Параметры:

ИмяОписание
$output

Возвращает: null

  • Отправляет HTTP-заголовки клиенту
  • Сохраняет открытую сессию
  • Закрывает буферы вывода
  • Отправляет HTTP-заголовок Content-Length
  • Отправляет данные

Примеры:

$Main->Request->send();

$Main->Request->send(false);
# Результат: Content-Length: 0

$Main->Request->send(404);
# Результат: 404 Not Found

Исходный код
    function send($output = null) {
        # HTTP-статус
        if (is_int($output)) $this->setStatus($output);

        # HTTP-статус
        $this->sendStatus();
        # HTTP-заголовки
        $this->sendHeader();
        # COOKIE
        $this->sendCookie();

        # Буферы вывода
        if ($status = ob_get_status()) {
            for ($i = $status['level'] - $this->ob_status['level']; $i > 1; $i --) ob_end_flush();
            $html = ob_get_clean();
            if ($output === false) $html = "";
            elseif (is_string($output)) $html = $output;
            # Content-Length
            if (!headers_sent()) {
                $header = "Content-Length: " . strlen($html);
                header($header);
            }
        } else {
            if (is_string($output)) $html = $output;
            else $html = '';
        }

        # Данные
        print $html;

        $this->Auth()->sessionCommit();
    }

sendStatus()

$Request->sendStatus();
Исходный код
    function sendStatus() {
        $this->status_header = ($_SERVER['SERVER_PROTOCOL'] ? $_SERVER['SERVER_PROTOCOL'] : "HTTP/1.1") . " " . $this->status;
        header($this->status_header);
    }

sendHeader()

$Request->sendHeader();
Исходный код
    function sendHeader() {
        foreach ($this->header as $header) header($header);
    }

sendCookie()

$Request->sendCookie();
Исходный код
    function sendCookie() {
        foreach ($this->cookie as $name => $a) {
            list($value, $expire, $path) = $a;
            if (!strlen($value)) $expire = 1;
            setcookie($name, $value, $expire, $path);
        }
    }

sendFile()

$Request->sendFile($pathname);

Параметры:

ИмяОписание
$pathname

Возвращает: true

Исходный код
    function sendFile($pathname) {
        if ((strpos($pathname, '/..') !== false) || (strpos($pathname, '../') !== false) || (strpos($pathname, '.php') !== false)) {
            $this->setStatus(403);
            return true;
        }
        if (!$st = @stat($pathname)) {
            $this->setStatus(404);
            return true;
        }
        $etag = '"' . dechex($st['mtime']) . '-' . dechex($st['size']) . '"';
        $lastModified = $this->dateRfc2822($st['mtime']);
        $ifNoneMatch = $_SERVER['HTTP_IF_NONE_MATCH'];
        $ifModifiedSince = $_SERVER['HTTP_IF_MODIFIED_SINCE'];
        $notModified = null;
        if (isset($ifModifiedSince)) {
            $ifModifiedSince = strtotime($ifModifiedSince);
            if (($ifModifiedSince > 0) && (intval($ifModifiedSince) === intval($st['mtime']))) $notModified = true;
            else $notModified = false;
        }
        if (($notModified !== false) && isset($ifNoneMatch)) {
            if ($ifNoneMatch === $etag) $notModified = true;
            else $notModified = false;
        }
        while (ob_end_clean()) {}
        ob_start();
        $this->addHeader('ETag: ' . $etag);
        $this->addHeader('Last-Modified: ' . $lastModified);
        if ($notModified) {
            $this->setStatus(304);
        } else {
            readfile($pathname);
        }
        return true;
    }

sendContent()

$Request->sendContent($content);
Исходный код
    function sendContent($content) {
        $etag = 'W/"' . strlen($content) . '-' . rtrim(base64_encode(md5($content, true)), '=') . '"';
        $ifNoneMatch = $_SERVER['HTTP_IF_NONE_MATCH'];
        $notModified = null;
        if (isset($ifNoneMatch)) {
            if ($ifNoneMatch === $etag) $notModified = true;
            else $notModified = false;
        }
        while (ob_end_clean()) {}
        ob_start();
        $this->addHeader('ETag: ' . $etag);
        if ($notModified) {
            $this->setStatus(304);
        } else {
            print $content;
        }
        return true;
    }

getSelf()

$Request->getSelf($href=null);

Получение URI запроса без начального /

Параметры:

ИмяОписание
$href

URL или URI запроса

Возвращает: string

Возвращает корректный URI запроса

  • Удаляет название протокола и имя хоста из запроса
  • Удаляет //, .., /., ./ из запроса
  • Удаляет index.php из запроса

Примеры:

$Main->Request->getSelf('http://www.ru/');
# Результат: ''

$Main->Request->getSelf('/news/index.php');
# Результат: 'news'

$Main->Request->getSelf('/news/1.html');
# Результат: 'news/1.html'

Исходный код
    function getSelf($href = null) {
        if (!isset($href)) {
            $href = $_SERVER['REQUEST_URI'];
        } elseif (strpos($href, '://') !== false) {
            if ($info = parse_url($href)) {
                $href = $info['path'];
            } else {
                $href = '/';
            }
        }
        $self = trim(preg_replace('~[\\./]+/~', '/', array_shift(explode('?', rawurldecode($href), 2))), '/');
        if (substr($self, -9) === 'index.php') $self = trim(substr($self, 0, -9), '/');
        return $self;
    }

getPath()

$Request->getPath($href=null);
Исходный код
    function getPath($href = null) {
        if (!isset($href)) {
            $href = $_SERVER['REQUEST_URI'];
        } elseif (strpos($href, '://') !== false) {
            if ($info = parse_url($href)) {
                $href = $info['path'];
            } else {
                $href = '/';
            }
        }
        $path = preg_replace('~[\\./]+/~', '/', array_shift(explode('?', rawurldecode($href), 2)));
        return $path;
    }

getId()

$Request->getId($href=null);

Получение ID страницы

Параметры:

ИмяОписание
$href

URL или URI запроса

Возвращает: string

Примеры:

$Main->Request->getId('http://www.ru/');
# Результат: '-'

$Main->Request->getId('/news/index.php');
# Результат: 'news'

$Main->Request->getId('/news/1.html');
# Результат: '/news/1'

Исходный код
    function getId($href = null) {
        if (!isset($href) && isset($_GET['p'])) {
            $id = $_GET['p'];
        } else {
            $self = $this->getSelf($href);
            foreach ($this->extensions as $ext) if (substr($self, -strlen($ext)) == $ext) $self = substr($self, 0, -strlen($ext));
            if (strpos($self, "/") !== false) $id = "/$self";
            elseif (strlen($self)) $id = $self;
            else $id = "-";
        }
        if (strlen($id) != strcspn($id, "\0\r\n\"'<>")) $id = "404";
        return $id;
    }

addHeader()

$Request->addHeader($header, $prepend=false);

Добавление HTTP-заголовка

Параметры:

ИмяОписание
$header

HTTP-заголовок

$prepend

добавить заголовок в начало списка

Возвращает: null

Примеры:

$Main->Request->addHeader('Content-Type: text/html; charset=UTF-8');

Исходный код
    function addHeader($header, $prepend = false) {
        if ($prepend) array_unshift($this->header, $header);
        else array_push($this->header, $header);
    }

setStatus()

$Request->setStatus($status);

Установка HTTP-статуса ответа

Параметры:

ИмяОписание
$status

HTTP-статус

Возвращает: null

Примеры:

$Main->Request->setStatus(404);

$Main->Request->setStatus('404 Not Found');

$Main->Request->setStatus('401 Unauthorized');

Исходный код
    function setStatus($status) {
        if (is_int($status)) switch ($status) {
            case 100: $status = "100 Continue"; break;
            case 101: $status = "101 Switching Protocols"; break;
            case 200: $status = "200 OK"; break;
            case 201: $status = "201 Created"; break;
            case 202: $status = "202 Accepted"; break;
            case 203: $status = "203 Non-Authoritative Information"; break;
            case 204: $status = "204 No Content"; break;
            case 205: $status = "205 Reset Content"; break;
            case 206: $status = "206 Partial Content"; break;
            case 300: $status = "300 Multiple Choices"; break;
            case 301: $status = "301 Moved Permanently"; break;
            case 302: $status = "302 Found"; break;
            case 303: $status = "303 See Other"; break;
            case 304: $status = "304 Not Modified"; break;
            case 305: $status = "305 Use Proxy"; break;
            case 306: $status = "305"; break;
            case 307: $status = "307 Temporary Redirect"; break;
            case 400: $status = "400 Bad Request"; break;
            case 401: $status = "401 Unauthorized"; break;
            case 402: $status = "402 Payment Required"; break;
            case 403: $status = "403 Forbidden"; break;
            case 404: $status = "404 Not Found"; break;
            case 405: $status = "405 Method Not Allowed"; break;
            case 406: $status = "406 Not Acceptable"; break;
            case 407: $status = "407 Proxy Authentication Required"; break;
            case 408: $status = "408 Request Timeout"; break;
            case 409: $status = "409 Conflict"; break;
            case 410: $status = "410 Gone"; break;
            case 411: $status = "411 Length Required"; break;
            case 412: $status = "412 Precondition Failed"; break;
            case 413: $status = "413 Request Entity Too Large"; break;
            case 414: $status = "414 Request-URI Too Long"; break;
            case 415: $status = "415 Unsupported Media Type"; break;
            case 416: $status = "416 Requested Range Not Satisfiable"; break;
            case 417: $status = "417 Expectation Failed"; break;
            case 500: $status = "500 Internal Server Error"; break;
            case 501: $status = "501 Not Implemented"; break;
            case 502: $status = "502 Bad Gateway"; break;
            case 503: $status = "503 Service Unavailable"; break;
            case 504: $status = "504 Gateway Timeout"; break;
            case 505: $status = "505 HTTP Version Not Supported"; break;
        }
        $this->status = $status;
    }

setCookie()

$Request->setCookie($name, $value, $expire=0, $path="/");
Исходный код
    function setCookie($name, $value, $expire = 0, $path = "/") {
        $_COOKIE[$name] = $value = strval($value);
        $this->cookie[$name] = array($value, $expire, $path);
    }

setSession()

$Request->setSession($session, $remember=false, $expire=0, $path='/');
Исходный код
    function setSession($session, $remember = false, $expire = 0, $path = '/') {
        setcookie("session", $session, $expire, $path);
        if ($remember || (!$remember && $_COOKIE['remember'])) setcookie('remember', $remember ? 'Y' : '', $expire, $path);
    }

getHost()

$Request->getHost($href=null);

Получение имени хоста

Параметры:

ИмяОписание
$href

URL запроса

Возвращает: string

Примеры:

$Main->Request->getHost();
# Результат: $_SERVER['HTTP_HOST'];

$Main->Request->getHost('http://www.ru/');
# Результат: 'www.ru'

Исходный код
    function getHost($href = null) {
        if (isset($href)) {
            if ($info = parse_url($href)) return $info['host'];
        } else {
            if (isset($_SERVER['HTTP_HOST'])) return $_SERVER['HTTP_HOST'];
            else return $this->Conf()->get("host");
        }
    }

stripWww()

$Request->stripWww($host);

Удаление www. из имени хоста

Параметры:

ИмяОписание
$host

имя хоста

Возвращает: string

Исходный код
    function stripWww($host) {
        return substr($host, 0, 4) == "www." ? substr($host, 4) : $host;
    }

href()

$Request->href($id=null);

Ссылка на страницу

Параметры:

ИмяОписание
$id

ID страницы

Возвращает: string

Примеры:

$Main->Request->href();
# Результат: $Main->Request->href($Main->Page->id)

$Main->Request->href('news');
# Результат: '/news.html'

Исходный код
    function href($id = null) {
        if (!isset($id)) $id = $this->Main()->Page->id;
        if ($id === '-' || $id === '') return '/';
        elseif ($id[0] === '/') return $id . $this->default_extension;
        else return '/' . $id . $this->default_extension;
    }

redirect()

$Request->redirect($href, $status=302);

Перенаправление

Параметры:

ИмяОписание
$href

адрес

$status

HTTP-статус

Исходный код
    function redirect($href, $status = 302) {
        $this->addHeader('Location: ' . $href);
        $this->setStatus($status);
        if (intval($status) === 301) {
            $this->addHeader('Cache-Control: private, no-cache, no-store, must-revalidate, max-age=0');
            $this->addHeader('Expires: ' . gmdate('D, j M Y H:i:s') . ' GMT');
            $this->addHeader('Pragma: no-cache');
        }
    }

absoluteUrl()

$Request->absoluteUrl($href);

Абсолютная ссылка

Параметры:

ИмяОписание
$href

ссылка

Возвращает: string

Исходный код
    function absoluteUrl($href) {
        if (strpos($href, "://") !== false) return $href;
        else return ($_SERVER['HTTPS'] && $_SERVER['HTTPS'] != "off" ? "https://" : "http://") . ($_SERVER['HTTP_HOST']) . ($href[0] === "/" ? "" : "/") . ($href);
    }

getQuery()

$Request->getQuery();
Исходный код
    function getQuery() {
        return $_SERVER['QUERY_STRING'];
    }

queryStringWithout()

$Request->queryStringWithout($key, $query=null);
Исходный код
    function queryStringWithout($key, $query = null) {
        if (!isset($query)) $query = $_SERVER['QUERY_STRING'];
        $query = preg_replace("~(^|&)" . preg_quote($key, "~") . "=[^&]*~", "", $query);
        return trim($query, "&");
    }

setCanonical()

$Request->setCanonical($href);
Исходный код
    function setCanonical($href) {
        $this->_canonical = $href;
    }

addCanonicalParam()

$Request->addCanonicalParam($name, $value);
Исходный код
    function addCanonicalParam($name, $value) {
        if (!isset($this->_canonical_param)) $this->_canonical_param = array();
        $this->_canonical_param[$name] = $value;
    }

getCanonical()

$Request->getCanonical();
Исходный код
    function getCanonical() {
        $Main = $this->Main();
        if (isset($this->_canonical)) return $this->_canonical;
        $href = $this->absoluteUrl($Main->Page->href());
        if ($a = $this->_canonical_param) {
            if (isset($a['page'])) {
                $page = $a['page'];
                unset($a['page']);
                $a['page'] = $page;
            }
            foreach ($a as $name => $value) {
                if (strlen($value)) {
                    if ($value[0] == " ") $value = "+" . rawurldecode(substr($value, 1));
                    else $value = rawurldecode($value);
                }
                $a[$name] = "$name=$value";
            }
            $href .= "?" . implode("&", $a);
        }
        return $href;
    }

setPrevPage()

$Request->setPrevPage($page);
Исходный код
    function setPrevPage($page) {
        $this->_prev_page = $page;
    }

getPrevLink()

$Request->getPrevLink();
Исходный код
    function getPrevLink() {
        if (!$page = $this->_prev_page) return;
        list($p, $q) = explode("?", $this->getCanonical(), 2);
        if (strlen($q)) $q = $this->queryStringWithout("page", $q);
        if ($page > 1) return $p . (strlen($q) ? "?$q&" : "?") . "page=$page";
        else return $p;
    }

setNextPage()

$Request->setNextPage($page);
Исходный код
    function setNextPage($page) {
        $this->_next_page = $page;
    }

getNextLink()

$Request->getNextLink();
Исходный код
    function getNextLink() {
        if (!$page = $this->_next_page) return;
        list($p, $q) = explode("?", $this->getCanonical(), 2);
        if (strlen($q)) $q = $this->queryStringWithout("page", $q);
        if ($page > 1) return $p . (strlen($q) ? "?$q&" : "?") . "page=$page";
        else return $p;
    }

dateRfc2822()

$Request->dateRfc2822($timestamp=null);
Исходный код
    function dateRfc2822($timestamp = null) {
        if ($timestamp === null) return gmdate('D, j M Y H:i:s') . ' GMT';
        else return gmdate('D, j M Y H:i:s', $timestamp) . ' GMT';
    }