Интерфейсы HTTP-сообщений
Этот документ описывает общие интерфейсы для представления сообщений HTTP, как описано в RFC 7230 и RFC 7231 и URI для использования с сообщениями HTTP, как описано в RFC 3986.
Сообщения HTTP являются основой веб-разработки. Веб-браузеры и клиенты HTTP, такие как cURL, создают сообщения запроса HTTP, которые отправляются на веб-сервер, который предоставляет ответное сообщение HTTP. Серверный код получает сообщение запроса HTTP и возвращает сообщение ответа HTTP.
HTTP-сообщения, как правило, абстрагируются от конечного пользователя, но нам, как разработчикам, обычно необходимо знать, как они структурированы и как получить к ним доступ или манипулировать ими для выполнения наших задач, будь то запрос к HTTP API или обработка входящего запроса.
Каждое сообщение HTTP-запроса имеет определенную форму:
POST /path HTTP/1.1
Host: example.com
foo=bar&baz=bat
Первая строка запроса называется «строка запроса» и содержит метод HTTP-запроса, цель запроса (обычно либо абсолютный URI, либо путь на веб-сервере) и версию протокола HTTP. Далее следует один или несколько заголовков HTTP, пустая строка и тело сообщения.
Сообщения HTTP-ответа имеют аналогичную структуру:
HTTP/1.1 200 OK
Content-Type: text/plain
This is the response body
Первая строка является «строкой состояния» и содержит версию протокола HTTP, код состояния HTTP и удобочитаемое описание кода состояния. Далее за "строкой состояния" следует один или несколько заголовков HTTP, пустая строка и тело сообщения.
Интерфейсы, описанные в этом документе, являются абстракциями HTTP-сообщений и составляющих их элементов.
Слова «НЕОБХОДИМО» / «ДОЛЖНО» ("MUST"), «НЕДОПУСТИМО» ("MUST NOT"), «ТРЕБУЕТСЯ» ("REQUIRED"), «НУЖНО» ("SHALL"), «НЕ ПОЗВОЛЯЕТСЯ» ("SHALL NOT"), «СЛЕДУЕТ» ("SHOULD"), «НЕ СЛЕДУЕТ» ("SHOULD NOT"), «РЕКОМЕНДУЕТСЯ» ("RECOMMENDED"), «МОЖЕТ» / «ВОЗМОЖНО» ("MAY") и «НЕОБЯЗАТЕЛЬНО» ("OPTIONAL") в этом документе следует понимать так, как это описано в RFC-2119 (и его переводе).
Ссылки
1. Спецификация
1.1 Сообщения
HTTP-сообщение — это либо запрос от клиента к серверу, либо ответ от сервера к клиенту.
Эта спецификация определяет интерфейсы для HTTP-сообщений: Psr\Http\Message\RequestInterface
и Psr\Http\Message\ResponseInterface
.
И Psr\Http\Message\RequestInterface
и Psr\Http\Message\ResponseInterface
расширяют
Psr\Http\Message\MessageInterface
. В то время как Psr\Http\Message\MessageInterface
МОЖЕТ быть
реализованы напрямую, разработчики ДОЛЖНЫ реализовывать
Psr\Http\Message\RequestInterface
и Psr\Http\Message\ResponseInterface
.
С этого момента пространство имен Psr\Http\Message
будет опущено при ссылке на эти интерфейсы.
1.2 HTTP-заголовки
Имена полей заголовков без учета регистра
Сообщения HTTP включают имена полей заголовков без учета регистра. Заголовки извлекаются по имени из классов,
реализующих MessageInterface
без учета регистра. Например, получение заголовка foo
вернет тот же результат, что и
получение заголовка FoO
. Точно так же установка заголовка Foo
перезапишет любое ранее установленное значение
заголовка foo
.
$message = $message->withHeader('foo', 'bar');
echo $message->getHeaderLine('foo');
// Выведет: bar
echo $message->getHeaderLine('FOO');
// Выведет: bar
$message = $message->withHeader('fOO', 'baz');
echo $message->getHeaderLine('foo');
// Выведет: baz
Несмотря на то, что заголовки могут быть получены без учета регистра, исходный регистр ДОЛЖЕН быть сохранен реализацией,
в частности, при извлечении с помощью getHeaders()
.
HTTP-приложения, которые не соответсвуют стандартам, могут понимать заголовки по разному. Поэтому полезно, чтобы разработчик мог указать регистр заголовков HTTP при создании запроса или ответа.
Заголовки с несколькими значениями
Чтобы разместить заголовки с несколькими значениями, но при этом обеспечить удобство работы с заголовками в виде строк,
заголовки можно извлекать из экземпляра MessageInterface
в виде массива или строки. Используйте
метод getHeaderLine()
, чтобы получить значение заголовка в виде строки, содержащей все значения заголовка без учета
регистра по имени, объединенному запятой.
Используйте getHeader()
, чтобы получить массив всех значений заголовков для конкретного заголовка без учета регистра
по имени.
$message = $message
->withHeader('foo', 'bar')
->withAddedHeader('foo', 'baz');
$header = $message->getHeaderLine('foo');
// $header содержит: 'bar,baz'
$header = $message->getHeader('foo');
// ['bar', 'baz']
Примечание. Не все значения заголовков можно объединить с помощью запятой (например,
Set-Cookie
). При работе с такими заголовками
При работе с такими заголовками классы на основе MessageInterface
ДОЛЖНЫ
полагаться на метод getHeader() для извлечения таких многозначных заголовков.
Заголовок Host
В запросах заголовок Host
обычно отражает хост URI, а также хост, используемый при установлении TCP-соединения.
Однако спецификация HTTP позволяет заголовку Host
отличаться от каждого из этих двух значений.
Реализации интерфейса ДОЛЖНЫ пытаться установить заголовок Host
из предоставленного URI, если заголовок Host
не
передан в заголовках.
RequestInterface::withUri()
по умолчанию заменяет заголовок Host
возвращаемого запроса на заголовок Host
,
соответствующий хост-компоненту переданного UriInterface
.
Вы можете согласиться на сохранение исходного состояния заголовка Host
,
передав значение true
для второго аргумента ($preserveHost
).
Если для этого аргумента установлено значение true
, возвращаемый запрос не будет обновлять заголовок Host
возвращаемого сообщения, если сообщение не содержит заголовка Host
.
В этой таблице показано, что getHeaderLine('Host')
вернет для запроса, возвращенного withUri()
с
аргументом $preserveHost
, установленным на true
, для различных исходных запросов и URI.
Заголовок Host запроса1 |
Компонент host запроса 2 |
URI host компонента3 |
Результат |
---|---|---|---|
'' | '' | '' | '' |
'' | foo.com | '' | foo.com |
'' | foo.com | bar.com | foo.com |
foo.com | '' | bar.com | foo.com |
foo.com | bar.com | baz.com | foo.com |
- 1 Значение заголовка
Host
перед операцией. - 2 Хост-компонент URI, составленный в запросе до операции.
- 3 Хост-компонент URI, внедряемый через
withUri()
.
1.3 Потоки
Сообщения HTTP состоят из начальной строки, заголовков и тела.
Тело сообщения HTTP может быть очень маленьким или очень большим.
Попытка представить тело сообщения в виде строки может легко потребовать больше памяти,
чем предполагалось, поскольку тело должно полностью храниться в памяти.
Попытка сохранить тело запроса или ответа в памяти помешает использованию этой реализации
для работы с большими телами сообщений. StreamInterface
используется для того,
чтобы скрыть детали реализации, когда поток данных читается или записывается.
В ситуациях, когда строка является подходящей реализацией сообщения,
могут использоваться встроенные потоки, такие как php://memory
и php://temp
.
StreamInterface предоставляет несколько методов, позволяющих эффективно читать, записывать и обходить потоки.
Потоки раскрывают свои возможности с помощью трех методов: isReadable()
,
isWritable()
и isSeekable()
. Эти методы могут использоваться участниками совместной работы над потоком, чтобы
определить, соответствует ли поток их требованиям.
Каждый экземпляр потока будет иметь различные возможности: он может быть только для чтения, только для записи или для чтения-записи. Он также может разрешать произвольный произвольный доступ (поиск в любом месте вперед или назад) или только последовательный доступ (например, в случае потока на основе сокета, канала или обратного вызова).
Наконец, StreamInterface
определяет метод __toString()
для упрощения извлечения или одновременной передачи всего
содержимого тела.
В отличие от интерфейсов запроса и ответа, StreamInterface
не моделирует неизменяемость.
В ситуациях, когда фактический поток PHP обернут, неизменяемость невозможно обеспечить,
поскольку любой код, взаимодействующий с ресурсом, потенциально может изменить его состояние
(включая положение курсора, содержимое и т. д.).
Мы рекомендуем, чтобы реализации использовали потоки только для чтения для запросов на
стороне сервера и ответов на стороне клиента. Потребители должны знать о том факте,
что экземпляр потока может быть изменчивым и, как таковой, может изменить состояние сообщения;
если есть сомнения, создайте новый экземпляр потока и прикрепите его к сообщению,
чтобы принудительно применить состояние.
1.4 Цели запросов и URI
Согласно RFC 7230, сообщения запроса содержат «цель запроса» в качестве второго сегмента строки запроса. Цель запроса может быть одной из следующих:
- Исходная форма, которая состоит из пути и, если есть, строки запроса такую запись часто называют относительным URL-адресом. Сообщения, передаваемые по протоколу TCP, обычно имеют исходную форму; схема и авторитетные данные обычно представлены только через переменные CGI.
- Абсолютная форма, состоящая из схемы ("[user-info@]host[:port]", где элементы в скобках являются необязательными), путь (если есть), строка запроса (если есть) и фрагмент (если есть). Такой формат часто называют абсолютным URI, и это единственная форма для указания URI, как подробно описано в RFC
- Эта форма обычно используется при выполнении запросов к HTTP-прокси.
- Авторитетная форма, состоящая только из полномочий. Обычно это используется только в запросах CONNECT для установления соединения между HTTP-клиентом и прокси-сервером.
- Форма-звездочка, состоящая исключительно из строки
*
и используемая с методом OPTIONS для определения общих возможностей веб-сервера.
Помимо этих целей запроса, часто существует «действующий URL», который отделен от цели запроса. Действующий URL-адрес не передается в HTTP-сообщении, но используется для определения протокола (http/https), порта и имени хоста для выполнения запроса.
Эффективный URL-адрес представлен посредством UriInterface
.
UriInterface
моделирует URI HTTP и HTTPS, как указано в RFC 3986 (основной вариант использования).
Интерфейс предоставляет методы для взаимодействия с различными частями URI, что устраняет необходимость повторного
анализа URI.
Он также определяет метод __toString()
для приведения смоделированного URI к его строковому представлению.
При получении цели запроса с помощью getRequestTarget()
по умолчанию этот метод будет
использовать объект URI и извлекать все необходимые компоненты для создания Исходная форма. Исходная форма на
сегодняшний день является наиболее распространенной целью запроса.
Если конечный пользователь желает использовать одну из трех других форм или если пользователь хочет явно переопределить
цель запроса, это можно сделать с помощью withRequestTarget()
.
Вызов этого метода не влияет на URI, так как он возвращается из getUri()
.
Например, пользователь может захотеть сделать запрос на сервер в форме звездочки:
$request = $request
->withMethod('OPTIONS')
->withRequestTarget('*')
->withUri(new Uri('https://example.org/'));
Этот пример может в конечном итоге привести к HTTP-запросу, который выглядит следующим образом:
OPTIONS * HTTP/1.1
Но HTTP-клиент сможет использовать эффективный URL-адрес (из getUri()
), чтобы определить протокол, имя хоста и TCP-порт.
HTTP-клиент ДОЛЖЕН игнорировать значения Uri::getPath()
и Uri::getQuery()
и вместо этого использовать значение, возвращаемое getRequestTarget()
, которое по умолчанию объединяет эти два значения.
Клиенты, которые решили не реализовывать 1 или более из 4 форм запроса-цели,
ДОЛЖНЫ по-прежнему использовать getRequestTarget()
.
Эти клиенты ДОЛЖНЫ отклонять цели запроса, которые они не поддерживают, и
НЕ ДОЛЖНЫ возвращаться к значениям из getUri()
.
RequestInterface
предоставляет методы для получения цели запроса или создания нового экземпляра с предоставленной целью запроса. По умолчанию, если в экземпляре специально не составлена цель запроса, getRequestTarget()
вернет исходную форму составленного URI (или "/", если URI не составлен). withRequestTarget($requestTarget)
создает новый экземпляр с указанной целью запроса и, таким образом, позволяет разработчикам создавать сообщения запроса, которые представляют три другие формы цели запроса (абсолютная форма, форма полномочий и форма звездочки).
1.5 Запросы на стороне сервера
RequestInterface
обеспечивает общее представление сообщения HTTP-запроса.
Однако запросы на стороне сервера требуют дополнительной обработки из-за особенностей среды на стороне сервера.
Обработка на стороне сервера должна учитывать общий интерфейс шлюза (CGI) и, в частности, абстракцию PHP и расширение CGI через его серверные API (SAPI).
PHP упростил работу с помощью суперглобальных переменных, таких как:
$_COOKIE
, который десериализует и обеспечивает упрощенный доступ к файлам HTTP cookie.$_GET
, который десериализует и обеспечивает упрощенный доступ к аргументам строки запроса.$_POST
, который десериализует и обеспечивает упрощенный доступ к urlencoded параметрам, отправленным через HTTP POST; в общем случае его можно рассматривать как результат разбора тела сообщения.$_FILES
, который предоставляет сериализованные метаданные для загрузки файлов.$_SERVER
, который обеспечивает доступ к переменным среды CGI/SAPI, которые обычно включают метод запроса, схему запроса, URI запроса и заголовки.
ServerRequestInterface
расширяет RequestInterface
, чтобы обеспечить абстракцию вокруг этих различных суперглобальных переменных.
Эта практика помогает уменьшить связь разработчиков с суперглобальными переменными, а также поощряет и продвигает возможность тестирования запросов.
Запрос к серверу предоставляет одно дополнительное свойство attributes
,
чтобы позволить разработчикам проводить самоанализ, декомпозировать и сопоставлять запрос с правилами, специфичными для приложения (такими как сопоставление пути, сопоставление схемы, сопоставление хоста и т. д.).
Таким образом, запрос сервера также может обеспечивать обмен сообщениями между несколькими запросами.
1.6 Загрузка файлов
ServerRequestInterface
определяет метод получения дерева загружаемых файлов в нормализованной структуре, где каждый лист является экземпляром
UploadedFileInterface
.
Суперглобальная переменная $_FILES
имеет некоторые хорошо известные проблемы при работе с массивами входных файлов.
Например, если у вас есть форма, которая отправляет массив файлов — например, входное имя «files», отправка «files[0]» и «files[1]» — PHP будет представлять это как:
[
'files' => [
'name' => [
0 => 'file0.txt',
1 => 'file1.html',
],
'type' => [
0 => 'text/plain',
1 => 'text/html',
],
/* и т.д. */
],
]
вместо ожидаемого:
[
'files' => [
0 => [
'name' => 'file0.txt',
'type' => 'text/plain',
/* и т.д. */
],
1 => [
'name' => 'file1.html',
'type' => 'text/html',
/* и т.д. */
],
],
]
В результате разработчики должны знать детали реализации этого языка и писать код под конкретные реализации.
Кроме того, существуют сценарии, в которых $_FILES
не заполняется при загрузке файлов:
- Когда метод HTTP не POST.
- При модульном тестировании.
- При работе в среде, отличной от SAPI, такой как ReactPHP.
В таких случаях данные должны быть заполнены по-другому. Например:
- Процесс может анализировать тело сообщения, чтобы обнаружить загруженные файлы. В таких случаях реализация может решить не записывать загружаемые файлы в файловую систему, а вместо этого заключать их в поток, чтобы уменьшить нагрузку на память, ввод-вывод и хранилище.
- В сценариях модульного тестирования разработчики должны иметь возможность заглушать и/или имитировать метаданные загрузки файлов, чтобы валидировать и проверять различные сценарии.
getUploadedFiles()
предоставляет нормализованную структуру для разработчиков.
Ожидается, что реализации:
- Соберают всю информацию для данной загрузки файла и используют ее для заполнения экземпляра
Psr\Http\Message\UploadedFileInterface
. - Повторно создавать отправленную древовидную структуру, где каждый лист является соответствующим экземпляром
Psr\Http\Message\UploadedFileInterface
для данного местоположения в дереве.
Упомянутая древовидная структура должна имитировать структуру именования, в которой были отправлены файлы.
В самом простом примере это может быть один именованный элемент формы, представленный как:
<input type='file' name='avatar' />
В этом случае структура в $_FILES
будет выглядеть так:
[
'avatar' => [
'tmp_name' => 'phpUxcOty',
'name' => 'my-avatar.png',
'size' => 90996,
'type' => 'image/png',
'error' => 0,
],
]
Нормализованная форма, возвращаемая функцией getUploadedFiles()
, будет следующей:
[
'avatar' => /* UploadedFileInterface instance */
]
В случае ввода с использованием обозначения массива для имени:
<input type='file' name='my-form[details][avatar]' />
$_FILES
в конечном итоге выглядит так:
[
'my-form' => [
'name' => [
'details' => [
'avatar' => 'my-avatar.png',
],
],
'type' => [
'details' => [
'avatar' => 'image/png',
],
],
'tmp_name' => [
'details' => [
'avatar' => 'phpmFLrzD',
],
],
'error' => [
'details' => [
'avatar' => 0,
],
],
'size' => [
'details' => [
'avatar' => 90996,
],
],
],
]
И соответствующее дерево, возвращаемое getUploadedFiles(), должно быть:
[
'my-form' => [
'details' => [
'avatar' => /* UploadedFileInterface instance */
],
],
]
В некоторых случаях вы можете указать массив файлов:
Upload an avatar: <input type='file' name='my-form[details][avatars][]' />
Upload an avatar: <input type='file' name='my-form[details][avatars][]' />
(Например, элементы управления JavaScript могут создавать дополнительные поля для загрузки файлов, чтобы разрешить загрузку нескольких файлов одновременно.)
В таком случае реализация спецификации должна агрегировать всю информацию, относящуюся к файлу с заданным индексом. Причина в том, что $_FILES
в таких случаях отклоняется от своей обычной структуры:
[
'my-form' => [
'name' => [
'details' => [
'avatars' => [
0 => 'my-avatar.png',
1 => 'my-avatar2.png',
2 => 'my-avatar3.png',
],
],
],
'type' => [
'details' => [
'avatars' => [
0 => 'image/png',
1 => 'image/png',
2 => 'image/png',
],
],
],
'tmp_name' => [
'details' => [
'avatars' => [
0 => 'phpmFLrzD',
1 => 'phpV2pBil',
2 => 'php8RUG8v',
],
],
],
'error' => [
'details' => [
'avatars' => [
0 => 0,
1 => 0,
2 => 0,
],
],
],
'size' => [
'details' => [
'avatars' => [
0 => 90996,
1 => 90996,
3 => 90996,
],
],
],
],
]
Приведенный выше массив $_FILES
будет соответствовать следующей структуре, возвращаемой функцией getUploadedFiles()
:
[
'my-form' => [
'details' => [
'avatars' => [
0 => /* UploadedFileInterface instance */,
1 => /* UploadedFileInterface instance */,
2 => /* UploadedFileInterface instance */,
],
],
],
]
Разработчики будут обращаться к индексу 1
вложенного массива, используя:
$request->getUploadedFiles()['my-form']['details']['avatars'][1];
Поскольку данные загруженных файлов являются производными (получены из $_FILES
или тела запроса), в интерфейсе также присутствует метод-мутатор withUploadedFiles()
, позволяющий делегировать нормализацию другому процессу.
В случае с исходными примерами реализация выглядит следующим образом:
$file0 = $request->getUploadedFiles()['files'][0];
$file1 = $request->getUploadedFiles()['files'][1];
printf(
"Received the files %s and %s",
$file0->getClientFilename(),
$file1->getClientFilename()
);
// "Received the files file0.txt and file1.html"
В этом предложении также признается, что реализации могут работать в средах, отличных от SAPI. Таким образом, UploadedFileInterface
предоставляет методы для обеспечения работы операций независимо от среды. Особенно:
moveTo($targetPath)
предоставляется как безопасная и рекомендуемая альтернатива вызовуmove_uploaded_file()
непосредственно для временного загружаемого файла. Реализации определят правильную операцию для использования в зависимости от среды.getStream()
вернет экземплярStreamInterface
. В не SAPI средах одна из предлагаемых возможностей состоит в том, чтобы анализировать отдельные загружаемые файлы в потокиphp://temp
, а не непосредственно в файлы; в таких случаях загружаемый файл отсутствует. Таким образом,getStream()
гарантированно работает независимо от среды.
В качестве примеров:
// Переместить файл в каталог загрузки
$filename = sprintf(
'%s.%s',
create_uuid(),
pathinfo($file0->getClientFilename(), PATHINFO_EXTENSION)
);
$file0->moveTo(DATA_DIR . '/' . $filename);
// Stream a file to Amazon S3.
// Assume $s3wrapper is a PHP stream that will write to S3, and that
// Psr7StreamWrapper is a class that will decorate a StreamInterface as a PHP
// StreamWrapper.
$stream = new Psr7StreamWrapper($file1->getStream());
stream_copy_to_stream($stream, $s3wrapper);
2. Пакеты
Описанные интерфейсы и классы предоставляются как часть Пакета psr/http-message.
3. Интерфейсы
3.1 Psr\Http\Message\MessageInterface
<?php
namespace Psr\Http\Message;
/**
* Сообщения HTTP состоят из запросов от клиента к серверу и ответов от сервера
* к клиенту.
* Этот интерфейс определяет методы, общие для каждого из них.
*
* Сообщения считаются неизменяемыми; все методы, которые могут изменить
* состояние, ДОЛЖНЫ быть реализованы таким образом, чтобы они сохраняли
* внутреннее состояние текущего сообщения и возвращали экземпляр,
* содержащий измененное состояние.
*
* @see http://www.ietf.org/rfc/rfc7230.txt
* @see http://www.ietf.org/rfc/rfc7231.txt
*/
interface MessageInterface
{
/**
* Извлекает версию протокола HTTP в виде строки.
*
* Строка ДОЛЖНА содержать только номер версии HTTP (например, «1.1», «1.0»).
*
* @return string Версия протокола HTTP.
*/
public function getProtocolVersion();
/**
* Возвращает экземпляр с указанной версией протокола HTTP.
*
* Строка ДОЛЖНА содержать только номер версии HTTP (например, «1.1», «1.0»).
*
* Этот метод ДОЛЖЕН быть реализован таким образом, чтобы сохранить
* неизменность сообщения, и ДОЛЖЕН возвращать экземпляр с новой
* версией протокола.
*
* @param string $version Версия протокола HTTP.
* @return static
*/
public function withProtocolVersion($version);
/**
* Извлекает все значения заголовков сообщений.
*
* Ключи представляют собой имя заголовка, которое будет отправлено по сети,
* а каждое значение представляет собой массив строк, связанных с заголовком.
*
* // Представляем заголовки в виде строки
* foreach ($message->getHeaders() as $name => $values) {
* echo $name . ': ' . implode(', ', $values);
* }
*
* // Генерируйте заголовки итеративно:
* foreach ($message->getHeaders() as $name => $values) {
* foreach ($values as $value) {
* header(sprintf('%s: %s', $name, $value), false);
* }
* }
*
* Хотя имена заголовков не чувствительны к регистру, getHeaders()
* сохранит точный регистр, в котором заголовки были изначально указаны.
*
* @return string[][] Возвращает ассоциативный массив заголовков сообщения.
* Каждый ключ ДОЛЖЕН быть именем заголовка,
* а каждое значение ДОЛЖНО быть массивом строк для этого заголовка.
*/
public function getHeaders();
/**
* Проверяет, существует ли заголовок по данному имени без учета регистра.
*
* @param string $name Имя поля заголовка без учета регистра.
* @return bool Возвращает true, если какие-либо имена заголовков совпадают
* с заданным именем заголовка, используя сравнение строк без учета регистра.
* Возвращает false, если в сообщении не найдено подходящего имени заголовка.
*/
public function hasHeader($name);
/**
* Извлекает значение заголовка сообщения по заданному имени без учета регистра.
*
* Этот метод возвращает массив всех значений заголовка данного имени заголовка
* без учета регистра.
*
* Если заголовок не отображается в сообщении, этот метод ДОЛЖЕН возвращать
* пустой массив.
*
* @param string $name Имя поля заголовка без учета регистра.
* @return string[] Массив строковых значений, предусмотренный для данного
* заголовка.
* Если заголовок не отображается в сообщении, этот метод ДОЛЖЕН возвращать
* пустой массив.
*/
public function getHeader($name);
/**
* Извлекает разделенную запятыми строку значений для одного заголовка.
*
* Этот метод возвращает все значения заголовка данного имени заголовка
* без учета регистра в виде строки, объединенной вместе с помощью запятой.
*
* ПРИМЕЧАНИЕ. Не все значения заголовков могут быть надлежащим образом представлены
* с помощью конкатенации запятых. Для таких заголовков используйте вместо этого
* getHeader() и укажите свой собственный разделитель при объединении.
*
* Если заголовок не отображается в сообщении, этот метод ДОЛЖЕН возвращать пустую строку.
*
* @param string $name Имя поля заголовка без учета регистра.
* @return string Строка значений, предусмотренных для данного заголовка,
* объединенных вместе с помощью запятой. Если заголовок не отображается в сообщении,
* этот метод ДОЛЖЕН возвращать пустую строку.
*/
public function getHeaderLine($name);
/**
* Возвращает экземпляр с предоставленным значением, заменяющим указанный заголовок.
*
* Хотя имена заголовков нечувствительны к регистру, эта функция сохраняет
* регистр заголовков и возвращает их из getHeaders().
*
* Этот метод ДОЛЖЕН быть реализован таким образом, чтобы сохранить
* неизменность сообщения, и ДОЛЖЕН возвращать экземпляр с новым и/или
* обновленным заголовком и значением.
*
* @param string $name Имя поля заголовка без учета регистра.
* @param string|string[] $value Значение(я) заголовка.
* @return static
* @throws \InvalidArgumentException для недопустимых имен заголовков или значений.
*/
public function withHeader($name, $value);
/**
* Возвращает экземпляр с указанным заголовком, к которому добавлено заданное значение.
*
* Существующие значения для указанного заголовка будут сохранены.
* Новые значения будут добавлены к существующему списку.
* Если заголовок ранее не существовал, он будет добавлен.
*
* Этот метод ДОЛЖЕН быть реализован таким образом, чтобы сохранить неизменность сообщения,
* и ДОЛЖЕН возвращать экземпляр с новым заголовком и/или значением.
*
* @param string $name Добавляемое имя поля заголовка без учета регистра.
* @param string|string[] $value Значение(я) заголовка.
* @return static
* @throws \InvalidArgumentException для недопустимых имен заголовков.
* @throws \InvalidArgumentException для недопустимых значений заголовка.
*/
public function withAddedHeader($name, $value);
/**
* Возвращает экземпляр без указанного заголовка.
*
* Разрешение заголовка ДОЛЖНО выполняться без учета регистра.
*
* Этот метод ДОЛЖЕН быть реализован таким образом, чтобы сохранить
* неизменность сообщения, и ДОЛЖЕН возвращать экземпляр, удаляющий
* именованный заголовок.
*
* @param string $name Имя поля заголовка без учета регистра, которое нужно удалить.
* @return static
*/
public function withoutHeader($name);
/**
* Получает тело сообщения.
*
* @return StreamInterface Возвращает тело в виде потока.
*/
public function getBody();
/**
* Возвращает экземпляр с указанным телом сообщения.
*
* Тело ДОЛЖНО быть объектом StreamInterface.
*
* Этот метод ДОЛЖЕН быть реализован таким образом, чтобы сохранить
* неизменность сообщения, и ДОЛЖЕН возвращать новый экземпляр с
* новым потоком тела.
*
* @param StreamInterface $body Тело.
* @return static
* @throws \InvalidArgumentException Когда тело недействительно.
*/
public function withBody(StreamInterface $body);
}
3.2 Psr\Http\Message\RequestInterface
<?php
namespace Psr\Http\Message;
/**
* Представляет исходящий запрос на стороне клиента.
*
* В соответствии со спецификацией HTTP этот интерфейс включает
* свойства для каждого из следующих элементов:
*
* - Версия протокола
* - HTTP-метод
* - URI
* - Заголовки
* - Тело сообщения
*
* Во время выполнения различные реализации ДОЛЖНЫ пытаться установить
* заголовок узла из предоставленного URI, если заголовок узла не предоставлен.
*
* Запросы считаются неизменяемыми; все методы, которые могут изменить
* состояние, ДОЛЖНЫ быть реализованы таким образом, чтобы они сохраняли
* внутреннее состояние текущего сообщения и возвращали экземпляр,
* содержащий измененное состояние.
*/
interface RequestInterface extends MessageInterface
{
/**
* Извлекает цель запроса сообщения.
*
* Извлекает цель запроса сообщения либо в том виде, в каком она
* появится (для клиентов), в том виде, в каком она появилась по
* запросу (для серверов), либо в том виде, в каком она была указана
* для экземпляра (см. withRequestTarget()).
*
* В большинстве случаев это будет исходная форма составленного URI,
* если только конкретная реализация не предоставила значение
* (см. withRequestTarget() ниже).
*
* Если URI недоступен и цель запроса не указана, этот метод
* ДОЛЖЕН вернуть строку «/».
*
* @return string
*/
public function getRequestTarget();
/**
* Возвращает экземпляр с определенной целью запроса.
*
* Если для запроса требуется цель запроса, отличная от формы источника,
* например, для указания абсолютной формы, формы полномочий или
* формы звездочки,bэтот метод может использоваться для создания экземпляра
* с указанной целью запроса, дословно.
*
* Этот метод ДОЛЖЕН быть реализован таким образом, чтобы сохранить
* неизменность сообщения, и ДОЛЖЕН возвращать экземпляр с измененной
* целью запроса.
*
* @see http://tools.ietf.org/html/rfc7230#section-5.3 (для различных форм
* запроса-цели, разрешенных в сообщениях запроса)
* @param mixed $requestTarget
* @return static
*/
public function withRequestTarget($requestTarget);
/**
* Извлекает HTTP-метод запроса.
*
* @return string Возвращает метод запроса.
*/
public function getMethod();
/**
* Возвращает экземпляр с предоставленным методом HTTP.
*
* Хотя имена методов HTTP обычно состоят из символов верхнего регистра,
* имена методов HTTP чувствительны к регистру, поэтому реализациям
* НЕ СЛЕДУЕТ изменять данную строку.
*
* Этот метод ДОЛЖЕН быть реализован таким образом, чтобы сохранить
* неизменность сообщения, и ДОЛЖЕН возвращать экземпляр с измененным
* методом запроса.
*
* @param string $method Метод с учетом регистра.
* @return static
* @throws \InvalidArgumentException для недопустимых методов HTTP.
*/
public function withMethod($method);
/**
* Извлекает экземпляр URI.
*
* Этот метод ДОЛЖЕН возвращать экземпляр UriInterface.
*
* @see http://tools.ietf.org/html/rfc3986#section-4.3
* @return UriInterface Возвращает экземпляр UriInterface,
* представляющий URI запроса.
*/
public function getUri();
/**
* Возвращает экземпляр с предоставленным URI.
*
* Этот метод ДОЛЖЕН обновлять заголовок узла возвращенного запроса
* по умолчанию, если URI содержит компонент узла. Если URI не содержит
* компонента хоста, любой ранее существовавший заголовок хоста ДОЛЖЕН
* быть перенесен в возвращаемый запрос.
*
* Вы можете согласиться на сохранение исходного состояния заголовка Host,
* установив для `$preserveHost` значение `true`. Когда для `$preserveHost`
* установлено значение `true`, этот метод взаимодействует с заголовком
* Host следующими способами:
*
* - Если заголовок узла отсутствует или пуст, а новый URI содержит компонент
* узла, этот метод ДОЛЖЕН обновить заголовок узла в возвращаемом запросе.
* - Если заголовок узла отсутствует или пуст, а новый URI не содержит
* компонента узла, этот метод НЕ ДОЛЖЕН обновлять заголовок узла
* в возвращаемом запросе.
* - Если заголовок Host присутствует и не является пустым,
* этот метод НЕ ДОЛЖЕН обновлять заголовок Host
* в возвращаемом запросе.
*
* Этот метод ДОЛЖЕН быть реализован таким образом, чтобы сохранить
* неизменность сообщения, и ДОЛЖЕН возвращать экземпляр, который имеет
* новый экземпляр UriInterface.
*
* @see http://tools.ietf.org/html/rfc3986#section-4.3
* @param UriInterface $uri Новый URI запроса для использования.
* @param bool $preserveHost Сохранять исходное состояние заголовка узла?
* @return static
*/
public function withUri(UriInterface $uri, $preserveHost = false);
}
3.2.1 Psr\Http\Message\ServerRequestInterface
<?php
namespace Psr\Http\Message;
/**
* Представляет входящий HTTP-запрос на стороне сервера.
*
* В соответствии со спецификацией HTTP этот интерфейс включает
* свойства для каждого из следующих элементов:
*
* - Версия протокола
* - HTTP-метод
* - URI
* - Заголовки
* - Тело сообщения
*
* Кроме того, он инкапсулирует все данные, поступающие в приложение из
* среды CGI и/или PHP, включая:
*
* - Значения, представленные в $_SERVER.
* - Любые предоставленные файлы cookie (обычно через $_COOKIE)
* - Аргументы строки запроса (обычно через $_GET или анализируются с помощью
* parse_str())
* - Загруженные файлы, если они есть (представлено в $_FILES)
* - Десериализованные параметры тела (обычно из $_POST)
*
* Значения $_SERVER ДОЛЖНЫ рассматриваться как неизменяемые, поскольку
* они представляют состояние приложения во время запроса; как таковые,
* не предусмотрено никаких методов, позволяющих изменять эти значения.
* Другие значения предоставляют такие методы, поскольку они могут быть
* восстановлены из $_SERVER или тела запроса и могут нуждаться в
* обработке во время приложения (например, параметры тела могут быть
* десериализованы на основе типа контента).
*
* Кроме того, этот интерфейс распознает полезность самопроверки запроса
* для получения и сопоставления дополнительных параметров (например,
* путем сопоставления пути URI, расшифровки значений cookie,
* десериализации содержимого тела, не закодированного в форме,
* сопоставления заголовков авторизации с пользователями и т. д.).
* Эти параметры хранятся в свойстве «атрибуты».
*
* Запросы считаются неизменяемыми; все методы, которые могут изменить
* состояние, ДОЛЖНЫ быть реализованы таким образом, чтобы они
* сохраняли внутреннее состояние текущего сообщения и возвращали
* экземпляр, содержащий измененное состояние.
*/
interface ServerRequestInterface extends RequestInterface
{
/**
* Получить параметры сервера.
*
* Извлекает данные, относящиеся к среде входящих запросов,
* обычно получаемые из суперглобальной переменной PHP $_SERVER.
* НЕ ТРЕБУЕТСЯ, чтобы данные изначально были в $_SERVER.
*
* @return array
*/
public function getServerParams();
/**
* Получить данные в файлах cookie.
*
* Извлекает файлы cookie, отправленные клиентом на сервер.
*
* Данные ДОЛЖНЫ быть совместимы со структурой суперглобального
* массива $_COOKIE.
*
* @return array
*/
public function getCookieParams();
/**
* Вернуть экземпляр с указанными файлами cookie.
*
* НЕ ТРЕБУЕТСЯ, чтобы данные поступали из суперглобала $_COOKIE,
* но ДОЛЖНЫ быть совместимы со структурой $_COOKIE.
* Как правило, эти данные создаются при создании экземпляра.
*
* Этот метод НЕ ДОЛЖЕН обновлять соответствующий заголовок Cookie
* экземпляра запроса или соответствующие значения в параметрах сервера.
*
* Этот метод ДОЛЖЕН быть реализован таким образом, чтобы сохранить
* неизменность сообщения, и ДОЛЖЕН возвращать экземпляр с
* обновленными значениями cookie.
*
* @param array $cookies Массив пар ключ/значение, представляющий файлы cookie.
* @return static
*/
public function withCookieParams(array $cookies);
/**
* Получить аргументы строки запроса.
*
* Извлекает десериализованные аргументы строки запроса, если они есть.
*
* Примечание: параметры запроса могут не синхронизироваться с параметрами
* URI или сервера. Если вам нужно убедиться, что вы получаете только исходные
* значения, вам может потребоваться проанализировать строку запроса из
* `getUri()->getQuery()` или из параметра сервера `QUERY_STRING`.
*
* @return array
*/
public function getQueryParams();
/**
* Возвращает экземпляр с указанными аргументами строки запроса.
*
* Эти значения ДОЛЖНЫ оставаться неизменными в течение входящего запроса.
* Они МОГУТ быть введены во время создания экземпляра, например,
* из суперглобального массива PHP $_GET, или МОГУТ быть получены
* из какого-либо другого значения, такого как URI. В тех случаях,
* когда аргументы анализируются из URI, данные ДОЛЖНЫ быть совместимы с тем,
* что возвращает PHP-функция parse_str() для целей обработки повторяющихся
* параметров запроса и обработки вложенных наборов.
*
* Установка аргументов строки запроса НЕ ДОЛЖНА изменять URI,
* хранящийся в запросе, или значения в параметрах сервера.
*
* Этот метод ДОЛЖЕН быть реализован таким образом, чтобы сохранить
* неизменность сообщения, и ДОЛЖЕН возвращать экземпляр с обновленными
* аргументами строки запроса.
*
* @param array $query Массив аргументов строки запроса, обычно из $_GET.
* @return static
*/
public function withQueryParams(array $query);
/**
* Получить нормализованные данные загрузки файла.
*
* Этот метод возвращает метаданные загрузки в нормализованном дереве,
* где каждый лист является экземпляром Psr\Http\Message\UploadedFileInterface.
*
* Эти значения МОГУТ быть подготовлены из $_FILES или тела сообщения во время
* создания экземпляра или МОГУТ вводиться через withUploadedFiles().
*
* @return array Дерево массива экземпляров UploadedFileInterface;
* пустой массив ДОЛЖЕН быть возвращен, если данные отсутствуют.
*/
public function getUploadedFiles();
/**
* Создает новый экземпляр с указанными загруженными файлами.
*
* Этот метод ДОЛЖЕН быть реализован таким образом, чтобы сохранить
* неизменность сообщения, и ДОЛЖЕН возвращать экземпляр с обновленными
* параметрами тела.
*
* @param array $uploadedFiles Дерево массива экземпляров UploadedFileInterface.
* @return static
* @throws \InvalidArgumentException если указана недопустимая структура.
*/
public function withUploadedFiles(array $uploadedFiles);
/**
* Получить все параметры, указанные в теле запроса.
*
* Если Content-Type запроса имеет значение application/x-www-form-urlencoded
* или multipart/form-data, а метод запроса — POST, этот метод ДОЛЖЕН
* возвращать содержимое $_POST.
*
* В противном случае этот метод может вернуть любые результаты десериализации
* содержимого тела запроса; поскольку синтаксический анализ возвращает
* структурированное содержимое, потенциальные типы ДОЛЖНЫ быть только
* массивами или объектами. Нулевое значение указывает на отсутствие
* основного содержимого.
*
* @return null|array|object Десериализованные параметры тела, если они есть.
* Обычно это массив или объект.
*/
public function getParsedBody();
/**
* Возвращает экземпляр с указанными параметрами тела.
*
* Они МОГУТ быть введены во время создания экземпляра.
*
* Если Content-Type запроса имеет значение
* application/x-www-form-urlencoded или multipart/form-data,
* а метод запроса — POST, используйте этот метод ТОЛЬКО
* для внедрения содержимого $_POST.
*
* НЕ ТРЕБУЮТСЯ чтобы данные поступали из $_POST, но они ДОЛЖНЫ
* быть результатом десериализации содержимого тела запроса.
* Десериализация/анализ возвращает структурированные данные,
* и поэтому этот метод принимает ТОЛЬКО массивы или объекты или
* нулевое значение, если ничего не было доступно для анализа.
*
* Например, если согласование содержимого определяет,
* что данные запроса представляют собой полезные данные JSON,
* этот метод можно использовать для создания экземпляра
* запроса с десериализованными параметрами.
*
* Этот метод ДОЛЖЕН быть реализован таким образом,
* чтобы сохранить неизменность сообщения, и
* ДОЛЖЕН возвращать экземпляр с обновленными параметрами тела.
*
* @param null|array|object $data Десериализованные данные тела.
* Обычно это массив или объект.
* @return static
* @throws \InvalidArgumentException если указан неподдерживаемый
* тип аргумента.
*/
public function withParsedBody($data);
/**
* Получить атрибуты, полученные из запроса.
*
* «Атрибуты» запроса могут использоваться для обеспечения
* возможности внедрения любых параметров, полученных из запроса:
* например, результаты операций сопоставления пути;
* результаты расшифровки файлов cookie;
* результаты десериализации тел сообщений, не закодированных в форме;
* и т. д.
* Атрибуты будут зависеть от приложения и запроса и МОГУТ
* быть изменяемыми.
*
* @return mixed[] Атрибуты, полученные из запроса.
*/
public function getAttributes();
/**
* Получить один производный атрибут запроса.
*
* Извлекает один производный атрибут запроса, как описано
* в getAttributes(). Если атрибут ранее не был установлен,
* возвращает значение по умолчанию, как указано.
*
* Этот метод устраняет необходимость в методе hasAttribute(),
* поскольку он позволяет указать значение по умолчанию,
* которое будет возвращено, если атрибут не найден.
*
* @see getAttributes()
* @param string $name Имя атрибута.
* @param mixed $default Значение по умолчанию, которое возвращается,
* если атрибут не существует.
* @return mixed
*/
public function getAttribute($name, $default = null);
/**
* Возвращает экземпляр с указанным производным атрибутом запроса.
*
* Этот метод позволяет установить один производный атрибут запроса,
* как описано в getAttributes().
*
* Этот метод ДОЛЖЕН быть реализован таким образом,
* чтобы сохранить неизменность сообщения, и
* ДОЛЖЕН возвращать экземпляр с обновленным атрибутом.
*
* @see getAttributes()
* @param string $name Имя атрибута.
* @param mixed $value Значение атрибута.
* @return static
*/
public function withAttribute($name, $value);
/**
* Возвращает экземпляр, который удаляет указанный производный
* атрибут запроса.
*
* Этот метод позволяет удалить один производный атрибут запроса,
* как описано в getAttributes().
*
* Этот метод ДОЛЖЕН быть реализован таким образом,
* чтобы сохранить неизменность сообщения, и ДОЛЖЕН
* возвращать экземпляр, удаляющий атрибут.
*
* @see getAttributes()
* @param string $name Имя атрибута.
* @return static
*/
public function withoutAttribute($name);
}
3.3 Psr\Http\Message\ResponseInterface
<?php
namespace Psr\Http\Message;
/**
* Представление исходящего ответа на стороне сервера.
*
* В соответствии со спецификацией HTTP этот интерфейс
* включает свойства для каждого из следующих элементов:
*
* - Версия протокола
* - Код состояния и фраза причины
* - Заголовки
* - Тело сообщения
*
* Ответы считаются неизменными; все методы, которые могут
* изменить состояние, ДОЛЖНЫ быть реализованы таким образом,
* чтобы они сохраняли внутреннее состояние текущего сообщения
* и возвращали экземпляр, содержащий измененное состояние.
*/
interface ResponseInterface extends MessageInterface
{
/**
* Получает код состояния ответа.
*
* Код состояния представляет собой 3-значный целочисленный
* код результата попытки сервера понять и удовлетворить запрос.
*
* @return int Код состояния.
*/
public function getStatusCode();
/**
* Возвращает экземпляр с указанным кодом состояния и,
* необязательно, фразой причины.
*
* Если фраза причины не указана, реализации МОГУТ выбрать
* по умолчанию RFC 7231 или рекомендованную IANA фразу
* причины для кода состояния ответа.
*
* Этот метод ДОЛЖЕН быть реализован таким образом,
* чтобы сохранить неизменность сообщения, и
* ДОЛЖЕН возвращать экземпляр с обновленным статусом и
* фразой причины.
*
* @see http://tools.ietf.org/html/rfc7231#section-6
* @see http://www.iana.org/assignments/http-status-codes/http-status-codes.xhtml
* @param int $code 3-значный целочисленный код результата,
* который необходимо установить.
* @param string $reasonPhrase Фраза причины для использования
* с предоставленным кодом состояния; если ничего не указано,
* реализации МОГУТ использовать значения по умолчанию,
* как это предлагается в спецификации HTTP.
* @return static
* @throws \InvalidArgumentException Для недопустимых аргументов
* кода состояния.
*/
public function withStatus($code, $reasonPhrase = '');
/**
* Получает фразу причины ответа, связанную с кодом состояния.
*
* Поскольку фраза причины не является обязательным элементом
* в строке состояния ответа, значение фразы причины МОЖЕТ быть пустым.
* Реализации МОГУТ возвращать фразу причины, рекомендованную RFC 7231
* по умолчанию (или те, которые перечислены в реестре кодов состояния
* HTTP IANA) для кода состояния ответа.
*
* @see http://tools.ietf.org/html/rfc7231#section-6
* @see http://www.iana.org/assignments/http-status-codes/http-status-codes.xhtml
* @return string Reason phrase; must return an empty string if none present.
*/
public function getReasonPhrase();
}
3.4 Psr\Http\Message\StreamInterface
<?php
namespace Psr\Http\Message;
/**
* Описывает поток данных.
*
* Как правило, экземпляр оборачивает поток PHP;
* этот интерфейс обеспечивает оболочку для наиболее распространенных
* операций, включая сериализацию всего потока в строку.
*/
interface StreamInterface
{
/**
* Считывает все данные из потока в строку от начала до конца.
*
* Этот метод ДОЛЖЕН пытаться найти начало потока перед чтением
* данных и читать поток, пока не будет достигнут конец.
*
* Предупреждение: Это может попытаться загрузить в память большой объем данных.
*
* Этот метод НЕ ДОЛЖЕН вызывать исключение, чтобы соответствовать
* операциям приведения строк PHP.
*
* @see http://php.net/manual/en/language.oop5.magic.php#object.tostring
* @return string
*/
public function __toString();
/**
* Закрывает поток и все базовые ресурсы.
*
* @return void
*/
public function close();
/**
* Отделяет любые базовые ресурсы от потока.
*
* После того, как поток был отсоединен, поток находится в
* непригодном для использования состоянии.
*
* @return resource|null Базовый поток PHP, если таковой имеется
*/
public function detach();
/**
* Получает размер потока, если он известен.
*
* @return int|null Возвращает размер в байтах, если он известен,
* или null, если он неизвестен.
*/
public function getSize();
/**
* Возвращает текущую позицию указателя чтения/записи файла.
*
* @return int Позиция указателя файла
* @throws \RuntimeException по ошибке.
*/
public function tell();
/**
* Возвращает true, если поток находится в конце потока.
*
* @return bool
*/
public function eof();
/**
* Возвращает, является ли поток доступным для поиска.
*
* @return bool
*/
public function isSeekable();
/**
* Ищет позицию в потоке.
*
* @see http://www.php.net/manual/en/function.fseek.php
* @param int $offset Смещение
* @param int $whence Указывает, как будет рассчитываться позиция
* курсора на основе смещения. Допустимые значения идентичны
* встроенным в PHP значениям $whence для `fseek()`. SEEK_SET:
* Установить позицию, равную байтам смещения. SEEK_CUR: Установить
* позицию как текущую позицию плюс смещение. SEEK_END: Установить
* позицию как конец потока плюс смещение.
* @throws \RuntimeException on failure.
*/
public function seek($offset, $whence = SEEK_SET);
/**
* Ищет начало потока.
*
* Если поток недоступен для поиска, этот метод вызовет исключение;
* в противном случае он выполнит seek(0).
*
* @see seek()
* @see http://www.php.net/manual/en/function.fseek.php
* @throws \RuntimeException при неудаче.
*/
public function rewind();
/**
* Возвращает, доступен ли поток для записи.
*
* @return bool
*/
public function isWritable();
/**
* Записывает данные в поток.
*
* @param string $string Строка, которая должна быть записана.
* @return int Возвращает количество байтов, записанных в поток.
* @throws \RuntimeException при неудаче.
*/
public function write($string);
/**
* Возвращает, доступен ли поток для чтения.
*
* @return bool
*/
public function isReadable();
/**
* Чтение данных из потока.
*
* @param int $length Считайте до $length байтов из объекта и верните их.
* Может быть возвращено меньше байтов, чем $length,
* если базовый вызов потока возвращает меньше байтов.
* @return string Возвращает данные, считанные из потока,
* или пустую строку, если нет доступных байтов.
* @throws \RuntimeException если возникает ошибка.
*/
public function read($length);
/**
* Возвращает оставшееся содержимое в строке
*
* @return string
* @throws \RuntimeException если чтение невозможно.
* @throws \RuntimeException если при чтении возникает ошибка.
*/
public function getContents();
/**
* Получает метаданные потока в виде ассоциативного массива
* или извлекает определенный ключ.
*
* Возвращаемые ключи идентичны ключам, возвращаемым функцией
* PHP stream_get_meta_data().
*
* @see http://php.net/manual/en/function.stream-get-meta-data.php
* @param string $key Конкретные метаданные для извлечения.
* @return array|mixed|null Возвращает ассоциативный массив,
* если ключ не указан. Возвращает конкретное значение ключа,
* если ключ предоставлен и значение найдено, или ноль,
* если ключ не найден.
*/
public function getMetadata($key = null);
}
3.5 Psr\Http\Message\UriInterface
<?php
namespace Psr\Http\Message;
/**
* Объект значения, представляющий URI.
*
* Этот интерфейс предназначен для представления URI в соответствии с
* RFC 3986 и предоставления методов для наиболее распространенных операций.
* Дополнительные функции для работы с URI могут быть предоставлены
* поверх интерфейса или извне. В основном он используется для HTTP-запросов,
* но может использоваться и в других контекстах.
*
* Экземпляры этого интерфейса считаются неизменяемыми;
* все методы, которые могут изменить состояние, ДОЛЖНЫ быть
* реализованы таким образом, чтобы они сохраняли внутреннее
* состояние текущего экземпляра и возвращали экземпляр,
* содержащий измененное состояние.
*
* Обычно заголовок Host также присутствует в сообщении запроса.
* Для запросов на стороне сервера схему обычно можно
* обнаружить в параметрах сервера.
*
* @see http://tools.ietf.org/html/rfc3986 (the URI specification)
*/
interface UriInterface
{
/**
* Получает компонент схемы URI.
*
* Если схемы нет, этот метод ДОЛЖЕН возвращать пустую строку.
*
* Возвращаемое значение ДОЛЖНО быть приведено к нижнему регистру
* в соответствии с RFC 3986. Section 3.1.
*
*
* Завершающий символ «:» не является частью схемы и
* НЕ ДОЛЖЕН добавляться.
*
* @see https://tools.ietf.org/html/rfc3986#section-3.1
* @return string Схема URI.
*/
public function getScheme();
/**
* Получите компонент полномочий URI.
*
* Если информация о полномочиях отсутствует,
* этот метод ДОЛЖЕН возвращать пустую строку.
*
* Синтаксис полномочий URI:
*
* <pre>
* [user-info@]host[:port]
* </pre>
*
* Если компонент порта не установлен или является стандартным
* портом для текущей схемы, его НЕ СЛЕДУЕТ включать.
*
* @see https://tools.ietf.org/html/rfc3986#section-3.2
* @return string The URI authority, in "[user-info@]host[:port]" format.
*/
public function getAuthority();
/**
* Получите компонент информации о пользователе URI.
*
* Если информация о пользователе отсутствует,
* этот метод ДОЛЖЕН возвращать пустую строку.
*
* Если пользователь присутствует в URI, это вернет это значение;
* кроме того, если пароль также присутствует,
* он будет добавлен к значению пользователя с двоеточием (":"),
* разделяющим значения.
*
* Завершающий символ «@» не является частью информации
* о пользователе и НЕ ДОЛЖЕН добавляться.
*
* @return string Информация о пользователе URI в формате
* «имя пользователя[:пароль]».
*/
public function getUserInfo();
/**
* Получите хост-компонент URI.
*
* Если хост отсутствует, этот метод ДОЛЖЕН возвращать пустую строку.
*
* Возвращаемое значение ДОЛЖНО быть приведено к
* нижнему регистру в соответствии с RFC 3986. Section 3.2.2.
*
*
* @see http://tools.ietf.org/html/rfc3986#section-3.2.2
* @return string Хост URI.
*/
public function getHost();
/**
* Получите компонент порта URI.
*
* Если порт присутствует, и он нестандартен для текущей схемы,
* этот метод ДОЛЖЕН вернуть его как целое число.
* Если порт является стандартным портом,
* используемым в текущей схеме, этот метод ДОЛЖЕН возвращать значение null.
*
* Если нет ни порта, ни схемы, этот метод ДОЛЖЕН возвращать нулевое значение.
*
* Если порт отсутствует, но присутствует схема, этот метод МОЖЕТ вернуть
* стандартный порт для этой схемы, но ДОЛЖЕН возвращать значение null.
*
* @return null|int URI-порт.
*/
public function getPort();
/**
* Получите компонент пути URI.
*
* Путь может быть либо пустым, либо абсолютным (начиная с косой черты),
* либо без корневого каталога (не начинающимся с косой черты).
* Реализации ДОЛЖНЫ поддерживать все три синтаксиса.
*
* Обычно пустой путь "" и абсолютный путь "/" считаются равными,
* как определено в RFC 7230, раздел 2.7.3. Но этот метод НЕ ДОЛЖЕН
* автоматически выполнять эту нормализацию, потому что в контекстах с
* обрезанным базовым путем, например. фронт-контроллера эта разница
* становится существенной. Задача пользователя — обрабатывать
* как «», так и «/».
*
* Возвращаемое значение ДОЛЖНО быть закодировано в процентах,
* но НЕ ДОЛЖНО дважды кодировать какие-либо символы.
* Чтобы определить, какие символы следует кодировать,
* обратитесь к RFC 3986, разделы 2 и 3.3.
*
* Например, если значение должно включать косую черту ("/"),
* не предназначенную для использования в качестве разделителя между
* сегментами пути, это значение ДОЛЖНО быть передано экземпляру
* в закодированной форме (например, "%2F").
*
* @see https://tools.ietf.org/html/rfc3986#section-2
* @see https://tools.ietf.org/html/rfc3986#section-3.3
* @return string Путь URI.
*/
public function getPath();
/**
* Получите строку запроса URI.
*
* Если строка запроса отсутствует, этот метод ДОЛЖЕН возвращать
* пустую строку.
*
* Ведущий "?" символ не является частью запроса и НЕ ДОЛЖЕН добавляться.
*
* Возвращаемое значение ДОЛЖНО быть закодировано в процентах,
* но НЕ ДОЛЖНО дважды кодировать какие-либо символы.
* Чтобы определить, какие символы следует кодировать, обратитесь к
* RFC 3986, разделы 2 и 3.4.
*
* Например, если значение в паре ключ/значение строки запроса
* должно включать амперсанд ("&"), не предназначенный для использования
* в качестве разделителя между значениями, это значение ДОЛЖНО быть
* передано в закодированной форме (например, "%26"). к экземпляру.
*
* @see https://tools.ietf.org/html/rfc3986#section-2
* @see https://tools.ietf.org/html/rfc3986#section-3.4
* @return string Строка запроса URI.
*/
public function getQuery();
/**
* Возвращает компонент фрагмента URI.
*
* Если фрагмента нет, этот метод ДОЛЖЕН возвращать пустую строку.
*
* Начальный символ «#» не является частью фрагмента и
* НЕ ДОЛЖЕН быть добавлен.
*
* Возвращаемое значение ДОЛЖНО быть закодировано в процентах,
* но НЕ ДОЛЖНО дважды кодировать какие-либо символы. Чтобы определить,
* какие символы следует кодировать, обратитесь к RFC 3986, разделы 2 и 3.5.
*
* @see https://tools.ietf.org/html/rfc3986#section-2
* @see https://tools.ietf.org/html/rfc3986#section-3.5
* @return string Фрагмент URI.
*/
public function getFragment();
/**
* Возвращает экземпляр с указанной схемой.
*
* Этот метод ДОЛЖЕН сохранять состояние текущего экземпляра и
* возвращать экземпляр, содержащий указанную схему.
*
* Реализации ДОЛЖНЫ поддерживать схемы "http" и "https" без
* учета регистра и МОГУТ использовать другие схемы,
* если это необходимо.
*
* Пустая схема эквивалентна удалению схемы.
*
* @param string $scheme Схема для использования с новым экземпляром.
* @return static Новый экземпляр с указанной схемой.
* @throws \InvalidArgumentException за недействительные схемы.
* @throws \InvalidArgumentException для неподдерживаемых схем.
*/
public function withScheme($scheme);
/**
* Вернуть экземпляр с указанной информацией о пользователе.
*
* Этот метод ДОЛЖЕН сохранять состояние текущего экземпляра и
* возвращать экземпляр, содержащий указанную информацию
* о пользователе.
*
* Пароль необязателен, но информация о пользователе ДОЛЖНА включать
* имя пользователя; пустая строка для пользователя эквивалентна
* удалению информации о пользователе.
*
* @param string $user Имя пользователя, используемое для полномочий.
* @param null|string $password Пароль, связанный с $user.
* @return static Новый экземпляр с указанной информацией о пользователе.
*/
public function withUserInfo($user, $password = null);
/**
* Вернуть экземпляр с указанным хостом.
*
* Этот метод ДОЛЖЕН сохранять состояние текущего экземпляра и
* возвращать экземпляр, содержащий указанный хост.
*
* Пустое значение хоста эквивалентно удалению хоста.
*
* @param string $host Имя хоста для использования с новым экземпляром.
* @return static Новый экземпляр с указанным хостом.
* @throws \InvalidArgumentException для недопустимых имен хостов.
*/
public function withHost($host);
/**
* Вернуть экземпляр с указанным портом.
*
* Этот метод ДОЛЖЕН сохранять состояние текущего экземпляра и
* возвращать экземпляр, содержащий указанный порт.
*
* Реализации ДОЛЖНЫ вызывать исключение для портов за
* пределами установленных диапазонов портов TCP и UDP.
*
*Пустое значение, указанное для порта, эквивалентно удалению
* информации о порте.
*
* @param null|int $port Порт для использования с новым экземпляром;
* нулевое значение удаляет информацию о порте.
* @return static Новый экземпляр с указанным портом.
* @throws \InvalidArgumentException для недопустимых портов.
*/
public function withPort($port);
/**
* Возвращает экземпляр с указанным путем.
*
* Этот метод ДОЛЖЕН сохранять состояние текущего экземпляра и
* возвращать экземпляр, содержащий указанный путь.
*
* Путь может быть либо пустым, либо абсолютным (начиная с косой черты),
* либо без корневого каталога (не начинающимся с косой черты).
* Реализации ДОЛЖНЫ поддерживать все три синтаксиса.
*
* Если предполагается, что путь HTTP относится к хосту, а не к пути,
* он должен начинаться с косой черты ("/"). Предполагается, что пути HTTP,
* не начинающиеся с косой черты, относятся к некоторому базовому пути,
* известному приложению или потребителю.
*
* Пользователи могут предоставлять как закодированные,
* так и декодированные символы пути. Реализации обеспечивают
* правильное кодирование, как указано в getPath().
*
* @param string $path Путь для использования с новым экземпляром.
* @return static Новый экземпляр с указанным путем.
* @throws \InvalidArgumentException для неверных путей.
*/
public function withPath($path);
/**
* Возвращает экземпляр с указанной строкой запроса.
*
* Этот метод ДОЛЖЕН сохранять состояние текущего экземпляра и
* возвращать экземпляр, содержащий указанную строку запроса.
*
* Пользователи могут предоставлять как закодированные,
* так и декодированные символы запроса.
* Реализации обеспечивают правильное кодирование,
* как описано в getQuery().
*
* Пустое значение строки запроса эквивалентно удалению строки запроса.
*
* @param string $query Строка запроса для использования с новым экземпляром.
* @return static Новый экземпляр с указанной строкой запроса.
* @throws \InvalidArgumentException для недопустимых строк запроса.
*/
public function withQuery($query);
/**
* Возвращает экземпляр с указанным фрагментом URI.
*
* Этот метод ДОЛЖЕН сохранять состояние текущего экземпляра и
* возвращать экземпляр, содержащий указанный фрагмент URI.
*
* Пользователи могут предоставлять как закодированные,
* так и декодированные символы фрагментов.
* Реализации обеспечивают правильное кодирование,
* как указано в getFragment().
*
* Пустое значение фрагмента эквивалентно удалению фрагмента.
*
* @param string $fragment Фрагмент для использования с новым экземпляром.
* @return static Новый экземпляр с указанным фрагментом.
*/
public function withFragment($fragment);
/**
* Возвращает строковое представление URI.
*
* В зависимости от того, какие компоненты URI присутствуют,
* результирующая строка является либо полным URI,
* либо относительной ссылкой в соответствии с RFC 3986, раздел 4.1.
* Метод объединяет различные компоненты URI,
* используя соответствующие разделители:
*
* - Если схема присутствует, она ДОЛЖНА иметь суффикс «:».
* - Если полномочия присутствуют, они ДОЛЖНЫ иметь префикс «//».
* - Путь может быть объединен без разделителей. Но есть два случая,
* когда необходимо изменить путь, чтобы сделать ссылку URI действительной,
* поскольку PHP не позволяет генерировать исключение в __toString():
- Если путь не имеет корня и присутствуют полномочия,
* путь ДОЛЖЕН иметь префикс «/».
- Если путь начинается с более чем одного «/» и
* отсутствуют полномочия, начальные косые черты ДОЛЖНЫ быть сокращены до одного.
- Если присутствует запрос, он ДОЛЖЕН иметь префикс «?».
- Если присутствует фрагмент, он ДОЛЖЕН иметь префикс "#".
*
* @see http://tools.ietf.org/html/rfc3986#section-4.1
* @return string
*/
public function __toString();
}
3.6 Psr\Http\Message\UploadedFileInterface
<?php
namespace Psr\Http\Message;
/**
* Объект, представляющий файл, загруженный с помощью HTTP-запроса.
*
* Экземпляры этого интерфейса считаются неизменяемыми;
* все методы, которые могут изменить состояние,
* ДОЛЖНЫ быть реализованы таким образом,
* чтобы они сохраняли внутреннее состояние текущего экземпляра
* и возвращали экземпляр, содержащий измененное состояние.
*/
interface UploadedFileInterface
{
/**
* Возвращает поток, представляющий загруженный файл.
*
* Этот метод ДОЛЖЕН возвращать экземпляр StreamInterface,
* представляющий загруженный файл. Цель этого метода —
* позволить использовать встроенную функциональность потока
* PHP для управления загрузкой файла, например,
* stream_copy_to_stream() (хотя для работы с такими функциями
* результат должен быть оформлен в встроенной оболочке потока PHP).
*
* Если метод moveTo() был вызван ранее,
* этот метод ДОЛЖЕН вызвать исключение.
*
* @return StreamInterface Потоковое представление загруженного файла.
* @throws \RuntimeException в случаях, когда поток недоступен.
* @throws \RuntimeException в случаях, когда поток не может быть создан.
*/
public function getStream();
/**
* Перемещает загруженный файл в новое место.
*
* Используйте этот метод как альтернативу move_uploaded_file().
* Этот метод гарантированно работает как в средах SAPI,
* так и в средах, отличных от SAPI. Реализации должны определить,
* в какой среде они находятся, и использовать соответствующий метод
* (move_uploaded_file(), rename() или потоковая операция)
* для выполнения операции.
*
* $targetPath может быть абсолютным или относительным путем.
* Если это относительный путь, разрешение должно быть таким же,
* как и в функции PHP rename().
*
* Исходный файл или поток ДОЛЖЕН быть удален после завершения.
*
* Если этот метод вызывается более одного раза,
* любые последующие вызовы ДОЛЖНЫ вызывать исключение.
*
* При использовании в среде SAPI, где $_FILES заполняется,
* при записи файлов через moveTo() СЛЕДУЕТ использовать
* is_uploaded_file() и move_uploaded_file(),
* чтобы обеспечить правильную проверку разрешений
* и статуса загрузки.
*
* Если вы хотите перейти к потоку, используйте getStream(),
* так как операции SAPI не могут гарантировать запись в места назначения потока.
*
* @see http://php.net/is_uploaded_file
* @see http://php.net/move_uploaded_file
* @param string $targetPath Путь, по которому следует переместить загруженный файл.
* @throws \InvalidArgumentException если указанный $targetPath недействителен.
* @throws \RuntimeException при любой ошибке во время операции перемещения.
* @throws \RuntimeException при втором или последующем вызове метода.
*/
public function moveTo($targetPath);
/**
* Получить размер файла.
*
* Реализации ДОЛЖНЫ возвращать значение, хранящееся в ключе "размер"
* файла в массиве $_FILES, если он доступен, поскольку PHP вычисляет
* это на основе переданного фактического размера.
*
* @return int|null Размер файла в байтах или null, если он неизвестен.
*/
public function getSize();
/**
* Возвращает ошибку, связанную с загруженным файлом.
*
* Возвращаемое значение ДОЛЖНО быть одной из констант PHP UPLOAD_ERR_XXX.
*
* Если файл был успешно загружен, этот метод ДОЛЖЕН вернуть UPLOAD_ERR_OK.
*
* Реализации ДОЛЖНЫ возвращать значение,
* хранящееся в ключе «ошибка» файла в массиве $_FILES.
*
* @see http://php.net/manual/en/features.file-upload.errors.php
* @return int Одна из констант PHP UPLOAD_ERR_XXX.
*/
public function getError();
/**
* Получить имя файла, отправленное клиентом.
*
* Не доверяйте значению, возвращаемому этим методом.
* Клиент может отправить вредоносное имя файла с
* намерением повредить или взломать ваше приложение.
*
* Реализации ДОЛЖНЫ возвращать значение,
* хранящееся в ключе «имя» файла в массиве $_FILES.
*
* @return string|null Имя файла, отправленное клиентом,
* или значение NULL, если оно не было указано.
*/
public function getClientFilename();
/**
* Возвращает тип мультимедиа, отправленный клиентом.
*
* Не доверяйте значению, возвращаемому этим методом.
* Клиент может отправить вредоносный тип носителя с намерением
* повредить или взломать ваше приложение.
*
* Реализации ДОЛЖНЫ возвращать значение,
* хранящееся в ключе "type" файла в массиве $_FILES.
*
* @return string|null Тип носителя, отправленный клиентом, или null,
* если он не был указан.
*/
public function getClientMediaType();
}