AAA

RFC 2068 — Протокол Передачи Гипертекста – HTTP/1.1

Статус данного документа

Этот документ определяет протокол дорожки стандартов Интернета (Internet standards track protocol) для семейства Интернета, и предназначен для обсуждения и предложений по усовершенствованию. Пожалуйста обратитесь к текущему изданию "Официальных стандартов протоколов Интернет" (STD 1) для выяснения состояния стандартизации и статуса этого протокола. Распространение данного документа неограничено.

Тезисы

Протокол передачи Гипертекста (HTTP) — протокол прикладного уровня для распределенных, совместных, многосредных информационных систем. Это общий, платформно-независимый, объектно-ориентированный протокол, который может использоваться во многих задачах, таких как сервера имен и распределенные системы управления объектами, посредством расширения методов запроса.

Возможность HTTP — это печать и обсуждение представления данных, позволяющее строить системы независимо от передаваемых данных. HTTP используется в World Wide Web (WWW) начиная с 1990 года. Эта спецификация определяет протокол, упоминаемый как "HTTP/1.1".

Содержание

1 Введение

1.1 Цель

Протокол передачи Гипертекста (HTTP) — протокол прикладного уровня для распределенных, совместных, многосредных информационных систем. HTTP используется в World Wide Web (WWW) начиная с 1990 года. Первой версией HTTP, известной как HTTP/0.9, был простой протокол для передачи необработанных данных через Интернет. HTTP/1.0, как определено в RFC 1945 [6], был улучшением этого протокола, позволяя сообщениям иметь MIME-подобный формат, содержащий метаинформацию о передаваемых данных и имел модифицированную семантику запросов/ответов. Однако, HTTP/1.0 недостаточно хорошо учитывал особенности работы с иерархическими прокси-серверами (hierarchical proxies), кэшированием, постоянными соединениями, и виртуальными хостами (virtual hosts). Кроме того, быстрое увеличение не полностью совместимых приложений, называющих тот протокол, который они использовали "HTTP/1.0", потребовало введения версии протокола, в которой были бы заложены возможности, позволяющие приложениям определять истинные возможности друг друга.

Эта спецификация определяет протокол "HTTP/1.1". Этот протокол содержит более строгие требования, чем HTTP/1.0, гарантирующие надежную реализацию возможностей.

Практически информационные системы требуют большей функциональности, чем просто загрузку информации, включая поиск, модификацию при помощи внешнего интерфейса, и аннотацию (annotation). HTTP предоставляет открытый набор методов, которые указывают цель запроса. Они основаны на дисциплине ссылки, обеспеченной Универсальным Идентификатором Ресурса (URI) [3][20], как расположение (URL) [4] или имя (URN), для идентификации ресурса, к которому этот метод применяется. Сообщения передаются в формате, подобном используемому электронной почтой, как определено Многоцелевыми Расширениями Электронной Почты (MIME).

HTTP также используется как обобщенный протокол связи между агентами пользователей и прокси-серверами/шлюзами (proxies/gateways) или другими сервисами Интернета, включая такие, как SMTP [16], NNTP [13], FTP [18], Gopher [2], и WAIS [10]. Таким образом, HTTP закладывает основы многосредного (hypermedia) доступа к ресурсам для разнообразных приложений.

1.2 Требования

Эта спецификация использует те же самые слова для определения требований к реализации протокола, что и RFC 1123 [8]. Эти слова следующие:

Реализация считается несовместимой, если нарушено хотя бы одно НЕОБХОДИМЫХ требований спецификации протокола. Реализация, удовлетворяющая всем НЕОБХОДИМЫМ и РЕКОМЕНДУЕМЫМ тредованиям называется полностью совместимой, а удовлетворяющая всем НЕОБХОДИМЫМ, но не всем РЕКОМЕНДУЕМЫМ требованиям называется условно совместимой.

1.3 Терминология

Эта спецификация использует ряд терминов для описания роли участников, некоторых объектов, и HTTP связи.

1.4 Общее описание

Протокол HTTP — это протокол запросов/ответов. Клиент посылает серверу запрос, содержащий метод запроса, URI, версию протокола, MIME-подобное сообщение, содержащее модификаторы запроса, клиентскую информацию, и, возможно, тело запроса, по соединению. Сервер отвечает строкой состояния, включающей версию протокола сообщения, код успешного выполнения или код ошибки, MIME-подобное сообщение, содержащее информацию о сервере, метаинформацию объекта, и, возможно, тело объекта. Связь между HTTP и MIME описана в приложении 19.4.

Большинство HTTP соединений инициализируется агентом пользователя и состоит из запроса, который нужно применить к ресурсу на некотором первоначальном сервере. В самом простом случае, он может быть выполнен посредством одиночного соединения (v) между агентом пользователя (UA) и первоначальным сервером (O).

   цепочка запросов --------------------->
UA -------------------v------------------- O
   <----------------------- цепочка ответов

Более сложная ситуация возникает, когда в цепочке запросов/ответов присутствует один или несколько посредников. Существуют три основных разновидности посредников: прокси-сервера, шлюзы, и туннели. Прокси-сервер является агентом-посредником, который получает запросы на некоторый URI в абсолютной форме, изменяет все сообщение или его часть, и отсылает измененный запрос серверу, идентифицированному URI. Шлюз — это принимающий агент, действующий как бы уровень выше некоторого другого сервера(ов) и, в случае необходимости, транслирующий запросы в протокол основного сервера. Туннель действует как реле между двумя соединениями не изменяя сообщения; туннели используются, когда связь нужно производить через посредника (например Firewall), который не понимает содержание сообщений.

   цепочка запросов ----------------------------------->
UA -----v----- A -----v----- B -----v----- C -----v----- O
   <------------------------------------ цепочка ответов

На последнем рисунке показаны три посредника (A, B, и C) между агентом пользователя и первоначальным сервером. Запросы и ответы передаются через четыре отдельных соединения. Это различие важно, так как некоторые опции HTTP соединения применимы только к соединению с ближайшим не туннельным соседом, некоторые только к конечным точкам цепочки, а некоторые ко всем соединениям в цепочке.

Хотя диаграмма линейна, каждый участник может быть задействован в нескольких соединениях одновременно. Например, B может получать запросы от других клиентов, а не только от A, и/или пересылать запросы к серверам, отличным от C, в то же время, когда он обрабатывает запрос от А.

Любая сторона соединения, которая не действует как туннель, может использовать внутренний кэш для обработки запросов. Эффект кэша заключается в том, что цепочка запросов/ответов сокращается, если один из участников в цепочке имеет кэшированный ответ, применимый к данному запросу. Далее иллюстрируется цепочка, возникающая в результате того, что B имеет кэшированую копию раннего ответа O (полеченного через C) для запроса, и который не кэшировался ни UA, ни A.

   цепочка запросов ------->
UA -----v----- A -----v----- B - - - - - - C - - - - - - O
   <-------- цепочка ответов

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

Фактически, имеется широкое разнообразие архитектур и конфигураций кэшей и прокси-серверов, в настоящее время разрабатываемых или развернутых в World Wide Web; эти системы включают национальные иерархии прокси-кэшей, которые сохраняют пропускную способность межокеанских каналов, системы, которые распространяют во много мест содержимое кэша, организации, которые распространяют подмножества кэшируемых данных на CD-ROM, и так далее. HTTP системы используются в корпоративных интранет-сетях с высокоскоростными линиями связи, и для доступа через PDA с маломощными линиями и неустойчивой связи. Цель HTTP/1.1 состоит в поддержании широкого многообразия конфигураций, уже построенных при введении ранних версий протокола, а также в удовлетворении потребностей разработчиков web приложений, требующих высокой надежности, по крайней мере надежных относительно индикации отказа.

HTTP соединение обычно происходит посредством TCP/IP соединений. Заданный по умолчанию порт TCP — 80, но могут использоваться и другие порты. HTTP также может быть реализован посредством любого другого протокола Интернета, или других сетей. HTTP необходима только надежная передача данных, следовательно может использоваться любой протокол, который гарантирует надежную передачу данных; отображение структуры запроса и ответа HTTP/1.1 на транспортные модули данных рассматриваемого протокола — вопрос, не решаемый этой спецификацией.

Большинство реализаций HTTP/1.0 использовало новое соединение для каждого обмена запросом/ответом. В HTTP/1.1, установленное соединение может использоваться для одного или нескольких обменов запросом/ответом, хотя соединение может быть закрыто по ряду причин (смотрите раздел 8.1).

2. Письменные соглашения и обобщенная грамматика

2.1 Увеличенная нормальная запись Бекуса-Наура (BNF)

Все механизмы, определенные этим документом, описаны как в обычной, так и в увеличенной нормальной записи Бекуса-Наура (BNF), подобной используемой в RFC 822 [9]. Разработчик должен быть знаком с такой формой записи, чтобы понять данную спецификацию. Увеличенная нормальная запись Бекуса-Наура включает следующие конструкции:

имя = определение
name = definition
   Имя правила - это просто его название (не включающее символов
   "<" и ">"), и отделяемое от определения символом равенства "=".
   Пробел важен только при выравнивании продолжающихся строк,
   используемых для указания определений правил, которые
   занимают более одной строки. Некоторые основные правила, такие
   как SP, LWS, HT, CRLF, DIGIT, ALPHA и т.д, представлены в
   верхнем регистре. Угловые скобки используются в определении
   всякий раз, когда их присутствие облегчает использование имен
   правил.

"литерал"
"literal"
   Кавычки окружают литеральный текст. Если не установлено иного,
   этот текст регистро-независим.

правило1 | правило2
rule1 | rule2
   Элементы, отделяемые полосой ("|") являются вариантами. Например,
   "да | нет" принимает значение либо да, либо нет.

(правило1 правило2)
(rule1 rule2)
   Элементы, включенные в круглые скобки обрабатываются как
   один элемент. Таким образом, "(elem (foo | bar) elem)"
   допускает последовательности лексем "elem foo elem" и
   "elem bar elem".

*правило
*rule
   Символ "*", предшествующий элементу, указывает повторение.
   Полная форма - "<n>*<m>element" означает минимум <n>, максимум
   <m> вхождений элемента. Значения по умолчанию - 0 и
   бесконечность. Таким образом запись "*(element)" допускает
   любое число повторений (в том числе ноль); запись "1*element"
   требует по крайней мере одно повторение; а "1*2element"
   допускает либо один, либо два повторения.

[правило]
[rule]
   В квадратные скобки заключают опциональные элементы; "[foo bar]"
   эквивалентно "*1(foo bar)".

N правило
N rule
   Точное количество повторений: "<n>(element)" эквивалентно
   "<n>*<n>(element)"; то есть присутствует точно <n> повторов
   элемента. Таким образом 2DIGIT - номер из 2 цифр, а 3ALPHA
   - строка из трех алфавитных символов.

#правило
#rule
   Конструкция "#" предназначена, подобно "*", для определения
   списка элементов. Полная форма - "<n>#<m>element" означает
   минимум <n>, максимум <m> вхождений элемента, отделенных одной
   или несколькими запятыми (","), и, возможно, линейным пробелом
   (LWS). Это обычно делает форму списков очень простой; правило
   типа "( *LWS element *( *LWS "," *LWS element)) " можно
   представить как "1#элемент". Везде, где используется эта
   конструкция, пустые элементы допускаются, но не учитываются при
   подсчете представленных элементов. То есть конструкция
   "(element), , (element)" допускается, но считаются в ней только
   два элемента. Следовательно там, где требуется по крайней мере
   один элемент, должен присутствовать по крайней мере  один не
   пустой элемент. Значения по умолчанию - 0 и бесконечность.
   Таким образом запись "#(element)" допускает любое число
   повторений (в том числе ноль); запись "1#element" требует по
   крайней мере одного повтора ненулевого элемента; а "1*2element"
   допускает один или два повтора.

; комментарий
; comment
   Точка с запятой, поставленная справа от текста правила, начинает
   комментарий, который продолжается до конца строки. Это - простой
   способ включения полезных пометок параллельно спецификациям.

подразумевая *LWS
implied *LWS
   Грамматика, описанная этой спецификацией основана на словах.
   За исключением случаев, в которых отмечено иное, линейный
   пробел (LWS) может быть включен между любыми двумя смежными
   словами (лексемой или строкой цитирования), и между смежными
   лексемами и разделителями (tspecials), не изменяя интерпретацию
   поля. Между любыми двумя лексемами должен существовать по
   крайней мере один разделитель (tspecials), так как иначе они
   интерпретируются как одна лексема.

2.2 Основные правила

Следующие правила используются в продолжение всей этой спецификации для описания основных конструкций синтаксического анализа. Кодированный набор символов US-ASCII определен в ANSI X3.4-1986 [21].

OCTET          = <любая 8-битная последовательность данных>

CHAR           = <любой US-ASCII символ (октеты 0 - 127)>

UPALPHA        = <любой US-ASCII символ верхнего регистра
                  "A".."Z">

LOALPHA        = <любой US-ASCII символ нижнего регистра
                  "a".."z">

ALPHA          = UPALPHA | LOALPHA

DIGIT          = <любая US-ASCII цифра "0".."9">

CTL            = <любой US-ASCII управляющий символ (октеты
                 0 - 31) и DEL (127)>

CR             = <US-ASCII CR, возврат каретки (13)>

LF             = <US-ASCII LF, перевод строки (10)>

SP             = <US-ASCII SP, пробел (32)>

HT             = <US-ASCII HT, метка горизонтальной
                  табуляции (9)>

<">            = <US-ASCII двойные кавычки (34)>

HTTP/1.1 определяет последовательность CR LF как метку конца строки во всех элементах протокола, за исключением тела объекта (смотрите приложение 19.3 о допустимых применениях (tolerant applications)). Метка конца строки внутри тела объекта определяется соответствыющим медиа типом, как описано в разделе 3.7.

CRLF           = CR LF

HTTP/1.1 заголовки занимают несколько строк, если следующая строка начинается с пробела или метки горизонтальной табуляции. Все незаполненное пространство строки, включая переход на следующую строку, имеет ту же семантику, что и SP.

LWS            = [CRLF] 1*( SP | HT )

Правило TEXT используется только для описательного содержимого поля и значений, которые не предназначены, для интерпретации синтаксическим анализатором сообщений. Слова *TEXT могут содержать символы из наборов символов (character sets), отличных от ISO 8859-1 [22], только когда они закодированы согласно правилам RFC 1522 [14].

TEXT           = <любой OCTET, за исключением CTLs,
                  но содержащий LWS>

Шестнадцатеричные цифры используются некоторыми элементами протокола.

HEX            = "A" | "B" | "C" | "D" | "E" | "F"
               | "a" | "b" | "c" | "d" | "e" | "f" | DIGIT

Многие значения полей заголовка HTTP/1.1 состоят из слов, разделенных LWS или специальными символами. Эти специальные символы ДОЛЖНЫ находиться в цитируемой строке (quoted string), чтобы быть использованными в качестве значения параметра.

token          = 1*<любой CHAR за исключением CTLs или
                    tspecials>

tspecials      = "(" | ")" | "<" | ">" | "@"
               | "," | ";" | ":" | "\" | <">
               | "/" | "[" | "]" | "?" | "="
               | "{" | "}" | SP | HT

В некоторые поля HTTP заголовка могут быть включены комментарии. Текст комментария окружается круглыми скобками. Комментарии допускаются только в полях, содержащих "comment" как часть определения значения поля. Во всех других полях круглые скобки рассматриваются частью значения поля.

comment        = "(" *( ctext | comment ) ")"

ctext          = <любой TEXT не включающий "(" and ")">

Строка текста анализируется как одно слово, если это цитирование, помеченное двойными кавычками.

quoted-string  = ( <"> *(qdtext) <"> )

qdtext         = <любой TEXT не включающий <">>

Символ наклонной черты влево ("\") может использоваться как односимвольный механизм цитирования только внутри конструкций комментария и строки цитирования (quoted-string).

quoted-pair    = "\" CHAR

3 Параметры протокола

3.1 Версия HTTP

HTTP использует схему нумерации типа "<major>.<minor>", для указания версии протокола. Стратегия версификации протокола предназначена для того, чтобы позволить отправителю указать формат сообщения и свои способности понимания для дальнейшей HTTP связи, прежде чем он получит что-либо посредством этой связи. При добавлении компонентов сообщения, которые не воздействуют на поведение связи, или компонентов, которые добавляются только к расширяемым значениям поля, номер версии не меняется. Когда внесенные в протокол изменения добавляют возможности, которые не изменяют общий алгоритм анализа сообщений, но которые расширяют семантику сообщения и подразумевают дополнительные возможности отправителя, увеличивается <Minor> номер. Когда формат сообщения протокола изменяется увеличивается <Major> номер.

Версия HTTP сообщения обозначается полем HTTP-version в первой строке сообщения.

HTTP-Version   = "HTTP" "/" 1*DIGIT "." 1*DIGIT

Обратите внимание, что major и minor числа ДОЛЖНЫ обрабатываться как отдельные целые числа и что каждое может состоять более чем из одной цифры. Таким образом, HTTP/2.4 — более низкая версия, чем HTTP/2.13, которая в свою очередь ниже чем HTTP/12.3. Нули ДОЛЖНЫ игнорироваться получателями и НЕ ДОЛЖНЫ посылаться.

Приложения, посылающие сообщения запросов или ответов, которые описывает эта спецификация, ДОЛЖНЫ включить HTTP версию (HTTP-version) "HTTP/1.1". Использование этого номера версии указывает, что посылающее приложение по крайней мере условно совместимо с этой спецификацией.

HTTP версия приложения — это самая высокая HTTP версия, для которой приложение является по крайней мере условно совместимым.

Приложения, реализующие прокси-сервера и шлюзы, должны быть внимательны, когда пересылают сообщения протокола различных версий. Начиная с момента, когда версия протокола указывает возможности отправителя, прокси-сервер/шлюз никогда НЕ ДОЛЖЕН посылать сообщения, версия которых больше, чем HTTP версия отправителя; если получена более высокая версия запроса, то прокси-сервер/шлюз ДОЛЖЕН или понизить версию запроса, отдав сообщение об ошибке, или переключиться на туннельное поведение. У запросов, версия которых ниже, чем HTTP версия прокси-сервера/шлюза МОЖНО перед пересылкой увеличить версию; ответ прокси-сервера/шлюза на этот запрос ДОЛЖЕН иметь ту же самую major версию, что и запрос.

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

3.2 Универсальные Идентификаторы Ресурсов (URI)

URI известны под многими именами: WWW адреса, Универсальные Идентификаторы Документов, Универсальные Идентификаторы Ресурсов (URI), и, в заключение, как комбинация Единообразных Идентификаторов Ресурса (Uniform Resource Locators, URL) и Единообразных Имен Ресурса (Uniform Resource Names, URN). HTTP определяет URL просто как строку определенного формата, которая идентифицирует — через имя, расположение, или любую другую характеристику — ресурс.

3.2.1 Общий синтаксис

URI в HTTP могут представляться в абсолютной (absolute) форме или относительно некоторой известной основы URI (relative), в зависимости от контекста их использования. Эти две формы различаются тем, что абсолютные URI всегда начинаются с имени схемы с двоеточием.

URI         = ( absoluteURI | relativeURI ) [ "#" fragment ]

absoluteURI = scheme ":" *( uchar | reserved )

relativeURI = net_path | abs_path | rel_path

net_path    = "//" net_loc [ abs_path ]
abs_path    = "/" rel_path
rel_path    = [ path ] [ ";" params ] [ "?" query ]

path        = fsegment *( "/" segment )
fsegment    = 1*pchar
segment     = *pchar

params      = param *( ";" param )
param       = *( pchar | "/" )

scheme      = 1*( ALPHA | DIGIT | "+" | "-" | "." )
net_loc     = *( pchar | ";" | "?" )

query       = *( uchar | reserved )
fragment    = *( uchar | reserved )

pchar       = uchar | ":" | "@" | "&" | "=" | "+"
uchar       = unreserved | escape
unreserved  = ALPHA | DIGIT | safe | extra | national

escape      = "%" HEX HEX
reserved    = ";" | "/" | "?" | ":" | "@" | "&" | "=" | "+"
extra       = "!" | "*" | "'" | "(" | ")" | ","
safe        = "$" | "-" | "_" | "."
unsafe      = CTL | SP | <"> | "#" | "%" | "<" | ">"
national    = <любой OCTET за исключением ALPHA, DIGIT,
                 reserved, extra, safe, и unsafe>

Полную информацию относительно синтаксиса и семантики URL смотрите RFC 1738 [4] И RFC 1808 [11]. Вышеуказанная нормальная запись Бекуса-Наура включает национальные символы, недозволенные в допустимых URL (это определено в RFC 1738), так как HTTP серверы позволяют использовать для представления части rel_path адресов набор незарезервированных символов, и, следовательно, HTTP прокси-сервера могут получать запросы URI, не соответствующие RFC 1738.

Протокол HTTP не накладывает a priori никаких ограничений на длины URI. Серверы ДОЛЖНЫ быть способны обработать URI любого ресурса, который они обслуживают, и им СЛЕДУЕТ быть в состоянии обрабатывать URI неограниченной длины, если они обслуживают формы, основанные на методе GET, которые могут генерировать такой URI. Серверу СЛЕДУЕТ возвращать код состояния 414 (URI запроса слишком длинный, Request-URI Too Long), если URI больше, чем сервер может обработать (смотрите раздел 10.4.15).

Обратите внимание: Серверы должны быть осторожны с URI, которые имеют длину более 255 байтов, потому что некоторые старые клиенты или прокси-сервера не могут правильно поддерживать эти длины.

3.2.2 HTTP URL

"Http" схема используется для доступа к сетевым ресурсам при помощи протокола HTTP. Этот раздел определяет схемо-определенный синтаксис и семантику для HTTP URL.

http_URL       = "http:" "//" host [ ":" port ] [ abs_path ]

host           = <допустимое доменное имя машины
                  или IP адрес (в точечно-десятичной форме),
                  как определено в разделе 2.1 RFC 1123>

port           = *DIGIT

Если порт пуст или не задан — используется порт 80. Это означает, что идентифицированный ресурс размещен в сервере, ожидающем TCP соединений на специфицированном порте port, компьютера host, и запрашиваемый URI ресурса — abs_path. Использования IP адресов в URL СЛЕДУЕТ избегать, когда это возможно (смотрите RFC 1900 [24]). Если abs_path не представлен в URL, он ДОЛЖЕН рассматриваться как "/" при вычислении запрашиваемого URI (Request-URI) ресурса (раздел 5.1.2).

3.2.3 Сравнение URI

При сравнении двух URI, чтобы решить соответствуют ли они друг другу или нет, клиенту СЛЕДУЕТ использовать чувствительное к регистру пооктетное (octet-by-octet) сравнение этих URI, со следующими исключениями:

Символы, отличные от тех, что находятся в "зарезервированных" ("reserved") и "опасных" ("unsafe") наборах (см. раздел 3.2) эквивалентны их кодированию как ""%" HEX HEX ".

Например следующие три URI эквивалентны:

http://abc.com:80/~smith/home.html
http://ABC.com/%7Esmith/home.html
http://ABC.com:/%7esmith/home.html

3.3 Форматы даты/времени

3.3.1 Полная дата

HTTP приложения исторически допускали три различных формата для представления даты/времени:

Sun, 06 Nov 1994 08:49:37 GMT  ; RFC 822, дополненный в RFC 1123
Sunday, 06-Nov-94 08:49:37 GMT ; RFC 850, переписанный как RFC 1036
Sun Nov  6 08:49:37 1994       ; формат asctime() ANSI C

Первый формат выбран в качестве стандарта Интернета и представляет подмножество фиксированной длины, как определено в RFC 1123 (модифицированном RFC 822). Второй формат находится в общем пользовании, но основан на устаревшем и потерявшем статус стандарта RFC 850 [12], описывающем форматы дат, он обладает тем недостатком, что год указывается не в четырехразрядной нотации. Клиенты и серверы HTTP/1.1, которые анализируют значение даты, ДОЛЖНЫ понимать все три формата (для совместимости с HTTP/1.0), но генерировать для представления значений дат в полях заголовка HTTP ДОЛЖНЫ только формат RFC 1123 .

Обратите внимание: Поощряется практика, при которой получатели значений дат здраво воспринимают значения дат, которые, возможно, посланы не HTTP приложениями, что имеет место при загрузке или регистрации сообщений через прокси-сервера/шлюзы к SMTP или NNTP.

Все без исключений форматы HTTP даты/времени ДОЛЖНЫ быть представлены в Greenwich Mean Time (GMT). В первых двух форматах данный факт указывается включением трехсимвольного сокращения "GMT" в качестве часового пояса. В asctime() формате это ДОЛЖНО подразумеваться при чтении.

HTTP-date    = rfc1123-date | rfc850-date | asctime-date

rfc1123-date = wkday "," SP date1 SP time SP "GMT"
rfc850-date  = weekday "," SP date2 SP time SP "GMT"
asctime-date = wkday SP date3 SP time SP 4DIGIT

date1        = 2DIGIT SP month SP 4DIGIT
               ; день месяц год (например 02 Jun 1982)

date2        = 2DIGIT "-" month "-" 2DIGIT
               ; день-месяц-год (напрмер 02-Jun-82)

date3        = month SP ( 2DIGIT | ( SP 1DIGIT ))
               ; месяц день (например, Jun  2)

time         = 2DIGIT ":" 2DIGIT ":" 2DIGIT
               ; 00:00:00 - 23:59:59

wkday        = "Mon" | "Tue" | "Wed"
             | "Thu" | "Fri" | "Sat" | "Sun"

weekday      = "Monday" | "Tuesday" | "Wednesday"
             | "Thursday" | "Friday" | "Saturday" | "Sunday"

month        = "Jan" | "Feb" | "Mar" | "Apr"
             | "May" | "Jun" | "Jul" | "Aug"
             | "Sep" | "Oct" | "Nov" | "Dec"

Обратите внимание: Эти требования — это требования к для форматам даты/времени, которые применяются внутри потока протокола HTTP. Клиентам и серверам не требуется использовать эти форматы для представления пользователю, регистрации запросов и т.д.

3.3.2 Разность секунд (delta seconds)

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

       delta-seconds  = 1*DIGIT

3.4 Кодовые таблицы (character sets)

HTTP использует то же самое определение термина "кодовая таблица", которое описано для MIME:

Термин "кодовая таблица" используется в данном документе, чтобы
сослаться на метод, использующий одну или несколько таблиц для
преобразования последовательности октетов в последовательность
символов. Стоит отметить, что однозначное преобразование в
обратном направлении не требуется, и что не все символы могут
быть доступны в данной кодовой таблице, и что кодовая таблица
может обеспечивать более чем одну последовательность октетов для
представления специфических символов. Это определение допускает
различные виды кодирования символов, от простых однотабличных
отображений типа US-ASCII до сложных методов, переключающих
таблицы, наподобие тех, которые используют методики ISO 2022.
Однако определение, связанное с именем кодовой таблицы MIME
ДОЛЖНО полностью определять отображение, которое преобразует
октеты в символы. В частности использование внешней информации
профилирования для определения точного отображения не
разрешается.

Обратите внимание: Это использование термина "кодовая таблица"
обычно упоминается как "кодирование символов". Однако, с тех пор
как HTTP и MIME совместно используют одиннаковую запись, важно,
чтобы совпадала также и терминология.

Кодовые таблицы HTTP идентифицируются лексемами, не чувствительными к регистру. Полный набор лексем определен реестром кодовых таблиц IANA [19].

charset = token

Хотя HTTP позволяет использовать в качестве значения charset произвольную лексему, любая лексема, которая имеет предопределенное значение в реестре кодовых таблиц IANA, ДОЛЖНА представлять набор символов, определенный в данном реестре. Приложениям СЛЕДУЕТ ограничить использование символьных наборов теми, которые определены в реестре IANA.

3.5 Кодирование содержимого (content codings)

Значение кодирования содержимого указывает какое преобразование кодирования было или будет применено к объекту. Кодирование содержимого используется прежде всего для сжатия или другого полезного преобразования к документу без потери идентификации основного медиа типа и информации. Часто, объект сохраняется в кодированной форме, затем передается, а потом декодируется получателем.

content-coding   = token

Все значения кодирования содержимого (content-coding) не чувствительны к регистру. HTTP/1.1 использует значения кодирования содержимого (content-coding) в полях заголовка Accept-Encoding (раздел 14.3) и Content-Encoding (раздел 14.12). Хотя значение описывает кодирование содержимого, но, что более важно — оно указывает, какой механизм декодирования потребуется для обратного процесса.

Internet Assigned Numbers Authority (IANA) действует как реестр для значений лексем кодирования содержимого (content-coding). Первоначально реестр содержал следующие лексемы:

Обратите внимание: Использовать названия программ для идентификации форматов кодирования не желательно и должно быть не понятно будущим кодированиям. Их использование здесь объясняется исторической практикой, но так делать не нужно. Для совместимости с предыдущими реализациями HTTP, приложения должны рассматривать "x-gzip" и "x-compress" как эквиваленты "gzip" и "compress" соответственно.

Новая лексема значения кодирования содержимого (content-coding) должна быть зарегистрирована; чтобы обеспечить взаимодействие между клиентами и серверами, спецификация алгоритма кодирования содержимого, необходимого для определения нового значения, должна быть открыто опубликована и адекватна для независимой реализации, а также соответствовать цели кодирования содержимого определенного в этом разделе.

3.6 Кодирование передачи (Transfer Codings)

Значения кодирования передачи используются для указания преобразования кодирования, которое было или должно быть применено к телу объекта (entity-body) в целях гарантирования "безопасной передачи" по сети. Оно отличается от кодирования содержимого тем, что кодирование передачи — это свойство сообщения, а не первоначального объекта.

transfer-coding         = "chunked" | transfer-extension

transfer-extension      = token

Все значения кодирования передачи (transfer-coding) не чувствительны к регистру. HTTP/1.1 использует значения кодирования передачи (transfer-coding) в поле заголовка Transfer-Encoding (раздел 14.40).

Кодирования передачи — это аналоги значений Content-Transfer-Encoding MIME, которые были разработаны для обеспечения безопасной передачи двоичных данных при использовании 7-битного обслуживания передачи. Однако безопасный транспорт имеет другое предназначение для чисто 8-битного протокола передачи. В HTTP единственая опасная характеристика тела сообщения вызвана сложностью определения точной длины тела сообщения (раздел 7.2.2), или желанием шифровать данные при пользовании общедоступным транспортом.

Кодирование по кускам (chunked encoding) изменяет тело сообщения для передачи его последовательностью кусков, каждый из которых имеет собственный индикатор размера, сопровождаемым опциональным завершителем, содержащим поля заголовка объекта. Это позволяет динамически создаваемому содержимому передаваться вместе с информацией, необходимой получателю для проверки полноты получения сообщения.

Chunked-Body   = *chunk
                 "0" CRLF
                 footer
                 CRLF

chunk          = chunk-size [ chunk-ext ] CRLF
                 chunk-data CRLF

hex-no-zero    = <HEX за исключением "0">

chunk-size     = hex-no-zero *HEX
chunk-ext      = *( ";" chunk-ext-name [ "=" chunk-ext-value ] )
chunk-ext-name = token
chunk-ext-val  = token | quoted-string
chunk-data     = chunk-size(OCTET)

footer         = *entity-header

Кодирование по кускам (chunked encoding) оканчивается куском нулевого размера, следующим за завершителем, оканчивающимся пустой строкой. Цель завершителя состоит в эффективном методе обеспечения информации об объекте, который сгенерирован динамически; приложения НЕ ДОЛЖНЫ посылать в завершителе поля заголовка, которые явно не предназначены для использования в завершителе, такие как Content-MD5 или будущие расширения HTTP для цифровых подписей и других возможностей.

Примерный процесс декодирования Chunked-Body представлен в приложении 19.4.6.

Все HTTP/1.1 приложения ДОЛЖНЫ быть в состоянии получать и декодировать кодирование передачи "по кускам" ("chunked" transfer coding), и ДОЛЖНЫ игнорировать расширения кодирования передачи, которые они не понимают. Серверу, который получил тело объекта со значением кодирования передачи, которое он не понимает, СЛЕДУЕТ возвратить ответ с кодом 501 (Не реализовано, Not Implemented) и разорвать соединение. Сервер НЕ ДОЛЖЕН посылать поля кодирования передачи (transfer-coding) HTTP/1.0 клиентам.

3.7 Медиа типы (Media Types)

HTTP использует Медиа Типы Интернета (Internet Media Types) в полях заголовка Content-Type (раздел 14.18) и Accept (раздел 14.1) для обеспечения открытой и расширяемой типизации данных и обсуждения типов.

media-type     = type "/" subtype *( ";" parameter )
type           = token
subtype        = token

Параметры могут следовать за type/subtype в форме пар атрибут/значение (attribute/value).

parameter      = attribute "=" value
attribute      = token
value          = token | quoted-string

Тип, подтип, и имена атрибутов и параметров не чувствительны к регистру. Значения параметров могут быть чувствительными к регистру, но могут быть и не чувствительны, в зависимости от семантики имени параметра. Линейный пробел (LWS) НЕ ДОЛЖЕН использоваться между типом и подтипом, между атрибутом и значением. Агенты пользователей, распознающие медиа типы, ДОЛЖНЫ обрабатывать (или подготавливать для обработки любыми внешними приложениями) параметры для тех типов MIME, которые описаны, и сообщать пользователю о обнаруженных проблемах.

Обратите внимание: Некоторые старые HTTP приложения не распознают параметры медиа типов. При посылке данных к таким HTTP приложениям реализации должны использовать параметры медиа типов только когда это требуется по определению типа/подтипа.

Значения медиа-типов регистрируются Internet Assigned Number Authority (IANA). Процесс регистрации медиа типа определен в RFC 2048 [17]. Использование не зарегистрированных медиа типов вводит в заблуждение.

3.7.1 Канонизация и предопределенные значения типа text

Медиа типы Интернета зарегистрированы в канонической форме. Вообще, тело объекта, передаваемое HTTP сообщением, ДОЛЖНО быть представлено в соответствующей каноническиой форме до передачи; исключение составляют типы "text", определяемые в следующем абзаце.

В канонической форме медиа подтипы типа "text" используют CRLF в качестве метки конца строки. HTTP ослабляет это требование и позволяет передавать текст размеченный таким образом, что еденичные CR или LF могут быть метками конца строки, правда это правило должно быть выполнено для всего тела объекта (entity-body). HTTP приложения ДОЛЖНЫ воспринимать CRLF, просто CR, и просто LF как представление конца строки в текстовых типах, переданных по HTTP. Кроме того, если текст представляется в кодовой таблице, которая не использует октеты 13 и 10 для CR и LF соответственно, что имеет место в некоторых многобайтовых кодовых таблицах, то HTTP позволяет использовать любые последовательности октетов, определенные этим набором символов для представления эквивалентов CR и LF в качестве кода конца строки. Эта гибкость в отношении концов строк применима только к текстовым типам в теле объекта; просто CR или просто LF НЕ ДОЛЖНЫ заменять CRLF внутри любой управляющей структуры HTTP (типа поля заголовка и разделителей типа multipart).

Если тело объекта кодируется при помощи Content-Encoding, то основные данные ДОЛЖНЫ быть в определенной выше форме до кодирования.

Параметр "charset" используется с некоторыми медиа типами для указания кодовой таблицы (раздел 3.4), используемой для представления данных. Если параметр "charset" не указан отправителем, то при получении по HTTP медиа подтипы типа "text" имеют значение "charset", по умолчанию равное "ISO-8859-1". Данные в кодовых таблицах или их подмножествах, отличных от "ISO-8859-1" ДОЛЖНЫ быть помечены соответствующим значением "charset".

Некоторое программное обеспечение HTTP/1.0 интерпретировало заголовок Content-Type без параметра "charset" неправильно, как означающее "должен предположить получатель". Отправители, желающие предусмотреть такое поведение МОГУТ включать параметр "charset" даже когда charset равен ISO-8859-1 и ДОЛЖНЫ сделать это, если известно, что это не запутает получателя.

К сожалению, некоторые старые HTTP/1.0 клиенты не работали правильно с определением параметра "charset". HTTP/1.1 получатели ДОЛЖНЫ отдавать приоритет метке "charset", поставленной отправителем; и те агенты пользователей, которые имеют возможность "предположить" charset ДОЛЖНЫ при первоначальном отображении документа использовать charset из поля content-type, если они поддерживают такой charset, а затем использовать собственные установки.

3.7.2 Типы Multipart

MIME предусматривает ряд типов "multipart" — формирующих пакет из одного или нескольких объектов внутри тела одного сообщения. Все типы mulptipart используют общий синтаксис, определеный в MIME [7], и ДОЛЖНЫ содержать разделительный параметр частью значения медиа типа. Тело сообщения — самостоятельный элемент протокола и, следовательно, ДОЛЖНО использовать только СRLF для представления концов строк между частями тела (body-parts). В отличие от MIME, окончание любого multipart сообщения ДОЛЖНО быть пустым; HTTP приложения НЕ ДОЛЖНЫ передавать окончание (даже если первоначальный multipart содержит заключение).

В HTTP части тела (body-parts) типа multipart МОГУТ содержать поля заголовка, которые являются значащими в примнении к этой части. Поле заголовка Content-Location (раздел 14.15) СЛЕДУЕТ включать в часть тела (body-part) каждого включенного объекта, который может быть идентифицирован URL.

Вообще говоря, HTTP агенту пользователя СЛЕДУЕТ следовать такому же или подобному поведению, которому следовал бы MIME агент пользователя после получения типа multipart. Если приложение получает незарегистрированный подтип multipart, оно ДОЛЖНО обрабатывать его как подтип "multipart/mixed".

Обратите внимание: тип "multipart/form-data" был специально определен для передачи данных формы, подходящих для обработки методом запроса POST, что описано в RFC 1867 [15].

3.8 Лексемы программ (Product Tokens)

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

product         = token ["/" product-version]
product-version = token

Примеры:

User-Agent: CERN-LineMode/2.15 libwww/2.17b3
Server: Apache/0.8.4

Лексемы программ должны быть короткими и по сути — использование их для рекламы или другой несущественной информации однозначно запрещено. Хотя в лексеме product-version может встречаться любой символ, все же ее следует использовать только для идентификатора версии (то есть, последовательным версиям одной и той же программы СЛЕДУЕТ иметь отличия только в части product-version лексемы product.

3.9 Качественные значения (Quality Values)

Обсуждение содержимого HTTP (раздел 12) использует короткие числа "с плавающей точкой" для указания относительной важности ("веса") различных оговоренных параметров. Вес — это нормализованое вещественное число в диапазоне от 0 до 1, где 0 — минимальное, а 1 — максимальное значение. HTTP/1.1 приложения НЕ ДОЛЖНЫ генерировать более трех цифр после десятичной точки. Пользовательским конфигурациям этих значений СЛЕДУЕТ также ограничиваться этим режимом.

qvalue         = ( "0" [ "." 0*3DIGIT ] )
               | ( "1" [ "." 0*3("0") ] )

"Качественные значения" — не корректное название, так как эти значения просто представляют отношение снижения производительности к желательному качеству.

3.10 Метки языков (Language Tags)

Метка языка идентифицирует естественный язык: разговорный, письменный, или другой используемый людьми для обмена информацмей с другими людьми. Машинные языки являются исключением. HTTP использует метки языка внутри полей Accept-Language и Content-Language.

Синтаксис и запись HTTP меток языка такие же, как определяемые RFC 1766 [1]. В резюме, метка языка состоит из одной или нескольких частей: метка первичного языка и, возможно пустой, ряд подчиненных меток:

language-tag  = primary-tag *( "-" subtag )

primary-tag   = 1*8ALPHA
subtag        = 1*8ALPHA

Внутри метки не допустим пробел и все метки не чувствительны к регистру. Пространство имен меток языка управляется IANA. Например метки содержат:

       en, en-US, en-cockney, i-cherokee, x-pig-latin

Любая двухсимвольная первичная метка является меткой аббревеатуры языка ISO 639, а любая двухсимвольная подчиненная метка является меткой кода страны ISO 3166. (Последние три метки из вышеперечисленных — не зарегистрированные метки; все, кроме последней — примеры меток, которые могли бы быть зарегистрированы в будущем.)

3.11 Метки объектов (Entity Tags)

Метки объектов используются для сравнения двух или более объектов от одного и того же запрошенного ресурса. HTTP/1.1 использует метки объекта в полях заголовка ETag (раздел 14.20), If-Match (раздел 14.25), If-None-Match (раздел 14.26), и If-Range (раздел 14.27). Определение того, как они используются и сравниваются в качестве меток проверки кэша находится в разделе 13.3.3. Метка объекта состоит из непрозрачной цитируемой строки (opaque quoted string), возможно предваренной индикатором слабости (weakness indicator).

entity-tag = [ weak ] opaque-tag

weak       = "W/"
opaque-tag = quoted-string

"Сильная метка объекта" ("strong entity tag") может быть разделена двумя объектами ресурса, только если они пооктетно эквивалентны.

"Слабая метка объекта" ("weak entity tag"), обозначяемая префиксом "W/", может быть разделена двумя объектами ресурса только если объекты эквивалентны и могли бы заменять друг друга без значительного изменения в семантике. Слабая метка объекта может использоваться только для слабого сравнения.

Метка объекта ДОЛЖНА быть уникальна среди всех версий всех объектов, связанных с конкретным ресурсом. Данное значение метки объекта может использоваться для объектов, полученных запросами различных URI без предположения эквивалентности этих объектов.

3.12 Еденицы измерения диапазонов (Range Units)

HTTP/1.1 позволяет клиенту запрашивать только часть объекта. HTTP/1.1 использует еденицы измерения диапазонов в полях заголовка Range (раздел 14.36) и Content-Range (раздел 14.17). Объект может быть разбит на части соответственно различным структурным модулям.

range-unit       = bytes-unit | other-range-unit

bytes-unit       = "bytes"
other-range-unit = token

Единственая еденица измерения диапазонов, определенная в HTTP/1.1 — это "bytes". Реализации HTTP/1.1 могут игнорировать диапазоны, определенные с использованием других едениц измерения. HTTP/1.1 был разработан, чтобы допускать реализации приложений, которые не зависят от знания диапазонов.

4. HTTP сообщение (HTTP Message)

4.1 Типы сообщений

HTTP сообщения делятся на запросы клиента серверу и ответы сервера клиенту.

HTTP-message   = Request | Response    ; сообщения HTTP/1.1

Сообщения запроса (раздел 5) и ответа (раздел 6) используют обобщенный формат сообщения RFC 822 [9] для пересылки объектов (полезной нагрузки сообщения). Оба типа сообщений выглядят следующим образом: сначала идет начальная строка (start-line), затем один или несколько полей заголовка (называемых также просто "заголовки"), затем пустая строка (то есть строка, равная CRLF), указывающая конец полей заголовка, а затем, возможно, тело сообщения.

generic-message = start-line
                  *message-header
                  CRLF
                  [ message-body ]

start-line      = Request-Line | Status-Line

В интересах ошибкоустойчивости, серверам СЛЕДУЕТ игнорировать все пустые строки, полученные перед строкой запроса (Request-Line). Другими словами, если сервер читает поток протокола и в самом начале сообщения получает CRLF, то ему следует этот CRLF игнорировать.

Обратите внимание: некоторые ошибочные реализации HTTP/1.0 клиентов генерируют дополнительные CRLF после запроса POST. Стоит вновь повторить, что это явно запрещено нормальной записью Бекуса-Наура. HTTP/1.1 клиент не должен добавлять дополнительные CRLF перед запросом и после него.

4.2 Заголовки сообщений

Поля заголовков HTTP, которые включают поля общих заголовков (general-header) (раздел 4.5), заголовков запроса (request-header) (раздел 5.3), заголовков ответа (response-header) (раздел 6.2), и заголовков объекта (entity-header) (раздел 7.1), имеют такой же обобщенный формат, что описан в разделе 3.1 RFC 822 [9]. Каждое поле заголовка состоит из имени, двоеточия (":") и значения поля. Имена полей не чувствительны к регистру. Значению поля может предшествовать любое число LWS, хотя предпочтителен одиночный SP. Поля заголовка могут занимать несколько строк. При этом каждая следующая строка начинается по крайней мере одним SP или HT. Приложениям СЛЕДУЕТ придерживаться "общей формы" ("common form") при генерации HTTP конструкций, так как могут существовать реализации, которые не в состоянии принимать что-либо кроме общих форм.

message-header = field-name ":" [ field-value ] CRLF

field-name     = token
field-value    = *( field-content | LWS )

field-content  = <октеты, составляющие значение поля и
                  состоящие или из *TEXT или из комбинаций
                  лексем, tspecials, и quoted-string>

Порядок, в котором получены поля заголовка с различными именами не имеет значения. Однако "хорошая практика" заключается в том, что сначала посылаются поля общих заголовков, затем поля заголовков запроса или заголовков ответа, и, наконец, поля заголовков объекта.

Несколько полей заголовка с одиннаковыми именами могут присутствовать в сообщении тогда, и только тогда, когда все значения полей, входящих в заголовок, определяют разделенный запятыми список [то есть #(value)]. ДОЛЖНО быть возможно объединить несколько таких полей заголовка в одну пару "имя поля: значение поля" (не измененяя этим семантику сообщения) присоединяя каждое последующее значение поля к первому через запятые. Порядок, в котором получены поля с одинаковыми именами, имеет значение для интерпретации объединенного значения поля, и, следовательно, прокси-сервер НЕ ДОЛЖЕН изменять порядок значений этого поля при пересылке.

4.3 Тело cообщения

Тело HTTP сообщения (message-body), если оно присутствует, используется для передачи тела объекта, связанного с запросом или ответом. Тело сообщения (message-body) отличается от тела объекта (entity-body) только в том случае, когда применяется кодирование передачи, что указывается полем заголовка Transfer-Encoding (раздел 14.40).

message-body = entity-body
             | <entity-body закодированно согласно
                Transfer-Encoding>

Поле Transfer-Encoding ДОЛЖНО использоваться для указания любого кодирования передачи, примененного приложением в целях гарантирования безопасной и правильной передачи сообщения. Поле Transfer-Encoding — это свойство сообщения, а не объекта, и, таким образом, может быть добавлено или удалено любым приложением в цепочке запросов/ответов.

Правила, устанавливающие допустимость тела сообщения в сообщении, отличны для запросов и ответов.

Присутствие тела сообщения в запросе отмечается добавлением к заголовкам запроса поля заголовка Content-Length или Transfer-Encoding. Тело сообщения (message-body) МОЖЕТ быть добавлено в запрос только когда метод запроса допускает тело объекта (entity-body) (раздел 5.1.1).

Включается или не включается тело сообщения (message-body) в сообщение ответа зависит как от метода запроса, так и от кода состояния ответа (раздел 6.1.1). Все ответы на запрос с методом HEAD НЕ ДОЛЖНЫ включать тело сообщения (message-body), даже если присутствуют поля заголовка объекта (entity-header), заставляющие поверить в присутствие объекта. Никакие ответы с кодами состояния 1xx (Информационные), 204 (Нет содержимого, No Content), и 304 (Не модифицирован, Not Modified) НЕ ДОЛЖНЫ содержать тела сообщения (message-body). Все другие ответы содержат тело сообщения, даже если оно имеет нулевую длину.

4.4 Длина сообщения

Когда тело сообщения (message-body) присутствует в сообщении, длина этого тела определяется одним из следующих методов (в порядке старшинства):

  1. Любое сообщение ответа, которое НЕ ДОЛЖНО включать тело сообщения (message-body) (например ответы с кодами состояния 1xx, 204, 304 и все ответы на запрос HEAD) всегда завершается пустой строкой после полей заголовка, независимо от полей заголовка объекта (entity-header fields), представленных в сообщении.
  2. Если поле заголовка Transfer-Encoding (раздел 14.40) присутствует и указывает на применение кодирования передачи "chunked", то длина определяется кодированием по кускам (chunked encoding) (раздел 3.6).
  3. Если поле заголовка Content-Length (раздел 14.14) присутствует, то его значение представляет длину тела сообщения (message-body) в байтах.
  4. Если сообщение использует медиа тип "multipart/byteranges", который саморазграничен, то он и определяет длину. Этот медиа тип НЕ ДОЛЖЕН использоваться, если отправитель не знает, что получатель может его обработать; присутствие в запросе заголовка Range с несколькими спецификаторами диапазонов байтов (byte-range) подразумевает, что клиент может анализировать multipart/byteranges ответы.
  5. Длина определяется закрытием соединения сервером. (Закрытие соединения не может использоваться для указания конца тела запроса, так как в этом случае у сервера не остается никакой возможности послать обратно ответ).

Для совместимости с HTTP/1.0 приложениями HTTP/1.1 запросы, содержащие тело сообщения (message-body) ДОЛЖНЫ включать допустимое поле заголовка Content-Length, если не известно, что сервер является HTTP/1.1 совместимым. Если запрос содержит тело сообщения (message-body), и Content-Length не указано, серверу СЛЕДУЕТ послать ответ с кодом состояния 400 (Испорченный Запрос, Bad Request), если он не может определить длину сообщения, или с кодом состояния 411 (Требуется длина, Length Required), если он настаивает на получении Content-Length.

Все HTTP/1.1 приложения, которые получают объекты, ДОЛЖНЫ понимать кодирование передачи типа "chunked" (раздел 3.6), таким образом разрешается использование данного механизма для таких сообщений, длина которых не может быть определена заранее.

Сообщения НЕ ДОЛЖНЫ одновременно включать и поле заголовка Content-Length и применять кодирование передачи типа "chunked". Если поступило сообщение с полем Content-Length и закодированное с применением кодирования передачи "chunked", то поле Content-Length ДОЛЖНО игнорироваться.

Если поле Content-Length присутствует в сообщении, которое допускает наличие тела сообщения (message-body), то значение поля ДОЛЖНО точно соответствовать числу октетов в теле сообщения. HTTP/1.1 агенты пользователя ДОЛЖНЫ информировать пользователя в случае получения и обнаружения недопустимой длины.

4.5 Общие поля заголовка

Имеется несколько полей заголовка, которые применяются как для сообщений запросов, так и для сообщений ответов, но которые не применяются к передаваемому объекту. Эти поля заголовка применяются только к передаваемому сообщению.

general-header = Cache-Control            ; Раздел 14.9
               | Connection               ; Раздел 14.10
               | Date                     ; Раздел 14.19
               | Pragma                   ; Раздел 14.32
               | Transfer-Encoding        ; Раздел 14.40
               | Upgrade                  ; Раздел 14.41
               | Via                      ; Раздел 14.44

Имена общих полей заголовка (general-header fields) могут быть надежно расширены только в сочетании с изменением версии протокола. Однако, новые или экспериментальные поля заголовка могут получить семантику общих полей заголовка (general-header fields), если все стороны соединения распознают их как общие поля заголовка. Нераспознанные поля заголовка обрабатываются как поля заголовка объекта (entity-header).

5. Запрос (Request)

Сообщение запроса от клиента к серверу содержит в первой строке: метод, который нужно применить к ресурсу, идентификатор ресурса и используемую версию протокола.

Request       = Request-Line              ; Раздел 5.1
                *( general-header         ; Раздел 4.5
                 | request-header         ; Раздел 5.3
                 | entity-header )        ; Раздел 7.1
                CRLF
                [ message-body ]          ; Раздел 7.2

5.1 Строка запроса (Request-Line)

Строка запроса (Request-Line) начинается с лексемы метода, затем следует запрашиваемый URI (Request-URI), версия протокола и CRLF. Эти элементы разделяются SP. В строке запроса (Request-Line) не допустимы CR и LF, исключение составляет конечная последовательность CRLF.

Request-Line   = Method SP Request-URI SP HTTP-Version CRLF

5.1.1 Метод (Method)

Лексема метода указывает метод, который нужно применить к ресурсу, идентифицированному запрашиваемым URI (Request-URI). Метод чувствителен к регистру.

Method         = "OPTIONS"                ; Раздел 9.2
              | "GET"                    ; Раздел 9.3
              | "HEAD"                   ; Раздел 9.4
              | "POST"                   ; Раздел 9.5
              | "PUT"                    ; Раздел 9.6
              | "DELETE"                 ; Раздел 9.7
              | "TRACE"                  ; Раздел 9.8
              | extension-method

extension-method = token

Список методов, применимых к ресурсу, может быть указан в поле заголовка Allow (раздел 14.7). Возврашаемый код состояния ответа всегда сообщает клиенту, допустим ли метод для ресурса в настоящее время, так как набор допустимых методов может изменяться динамически. Серверам СЛЕДУЕТ возвратить код состояния 405 (Метод не дозволен, Method Not Allowed), если метод известен серверу, но не применим для запрошенного ресурса, и 501 (Не реализовано, Not Implemented), если метод не распознан или не реализован сервером. Список методов, известных серверу, может быть указан в поле заголовка ответа Public (раздел 14.35).

Методы GET и HEAD ДОЛЖНЫ поддерживаться всеми универсальными (general-purpose) серверами. Остальные методы опциональны; однако, если вышеупомянутые методы реализованы, то они ДОЛЖНЫ иметь семантику, описанную в разделе 9.

5.1.2 Запрашиваемый URI (Request-URI).

Запрашиваемый URI (Request-URI) — это Единообразный Идентификатор Ресурса (URL, раздел 3.2), который идентифицирует ресурс запроса.

Request-URI    = "*" | absoluteURI | abs_path

Три опции для запрашиваемого URI (Request-URI) зависят от характера запроса. Звездочка "*" означает, что запрос обращается не к специфическому ресурсу, а к серверу непосредственно, и допускается только в том случае, когда используемый метод не обязательно обращается к ресурсу.

В качестве примера:

OPTIONS * HTTP/1.1

absoluteURI необходим, когда запрос производится через прокси-сервер. Прокси-сервер перенаправляет запрос на сервер или обслуживает его, пользуясь кэшем, и возвращает ответ. Обратите внимание, что прокси-сервер МОЖЕТ переслать запрос другому прокси-серверу или непосредственно серверу, определенному absoluteURI. Чтобы избежать зацикливания запроса прокси-сервер ДОЛЖЕН быть способен распознавать все имена сервера, включая любые псевдонимы, локальные разновидности, и числовые IP адреса. Request-Line может быть, например, таким:

GET http://www.w3.org/pub/WWW/TheProject.html HTTP/1.1

Чтобы обеспечить переход к absoluteURI во всех запросах в будущих версиях HTTP, все HTTP/1.1 серверы ДОЛЖНЫ принимать absoluteURI в запросах, хотя HTTP/1.1 клиенты будут генерировать их только в запросах к прокси-серверам.

Наиболее общая форма Request-URI — та, которая используется для идентификации ресурса на первоначальном сервере или шлюзе. В этом случае абсолютный путь URI (смотрите раздел 3.2.1, abs_path) ДОЛЖЕН быть передан как Request-URI, а сетевое расположение URI (net_loc) ДОЛЖНО быть передано в поле заголовка Host. Для последнего примера клиент, желающий получить ресурс непосредственно с первоначального сервера должен создать TCP соединение на 80 порт хоста "www.w3.org" и послать строки:

GET /pub/WWW/TheProject.html HTTP/1.1
Host: www.w3.org

и далее остаток запроса. Обратите внимание, что абсолютный путь не может быть пустым; если оригинальный URI пуст, то он ДОЛЖЕН запрашиваться как "/" (корневой каталог сервера).

Если прокси-сервер получает запрос без пути в Request-URI, и метод запроса допускает форму запроса "*", то последний прокси-сервер в цепочке запросов ДОЛЖЕН передать запрос, в котором Request-URI равен "*". Например запрос

OPTIONS http://www.ics.uci.edu:8001 HTTP/1.1

был бы передан прокси-сервером в виде

OPTIONS * HTTP/1.1
Host: www.ics.uci.edu:8001

после соединения с портом 8001 хоста "www.ics.uci.edu".

Request-URI передается в формате, определенном в разделе 3.2.1. Первоначальный сервер ДОЛЖЕН декодировать Request-URI, чтобы правильно интерпретировать запрос. Серверам СЛЕДУЕТ отвечать на недопустимые Request-URI соответствующим кодом состояния.

В запросах, которые передаются далее, прокси-сервера никогда НЕ ДОЛЖНЫ перезаписывать часть "abs_path" запрашиваемого URI (Request-URI), за исключением случая, отмеченного выше, когда пустой abs_path заменяется на "*", независимо от внутренней реализации прокси-сервера.

Обратите внимание: правило "ничто не перезаписывать" предохраняет прокси-сервера от изменения значения запроса, в котором первоначальный сервер неправильно использует не зарезервированные символы URL для своих целей. Реализаторам следует знать, что некоторые до-HTTP/1.1 прокси-сервера, как известно, перезаписывали Request-URI.

5.2 Ресурс, идентифицируемый запросом

Первоначальные HTTP/1.1 сервера ДОЛЖНЫ учитывать, что точный ресурс, идентифицированный интернет-запросом определяется исследованием как Request-URI, так и поля заголовка Host.

Первоначальный сервер, который не позволяет ресурсам отличаться по запрошенному хосту (host), МОЖЕТ игнорировать значение поля заголовка Host. (Но смотрите раздел 19.5.1 для других требований по поддержке Host в HTTP/1.1).

Первоначальный сервер, который различает ресурсы, основанные на запрошенном хосте (иногда называемые виртуальными хостами или vanity hostnames) ДОЛЖЕН использовать следующие правила для определения запрошенного в HTTP/1.1 запросе ресурса:

  1. Если Request-URI — это absoluteURI, то хост — это часть Request-URI. Любое значение поля заголовка Host в запросе ДОЛЖНО игнорироваться.
  2. Если Request-URI — не absoluteURI, а запрос содержит поле заголовка Host, то хост определяется значением поля заголовка Host.
  3. Если хоста, определенного правилами 1 или 2 не существует на сервере, код состояния ответа ДОЛЖЕН быть 400 (Испорченный Запрос, Bad Request).

Получатели HTTP/1.0 запроса, в котором недостает поля заголовка Host, МОГУТ пытаться использовать эвристику (например, исследовать путь в URI на предмет уникальности на каком-либо из хостов) чтобы определить какой точно ресурс запрашивается.

5.3 Поля заголовка запроса

Поля заголовка запроса позволяют клиенту передавать серверу дополнительную информацию о запросе и о самом клиенте. Эти поля действуют как модификаторы запроса с семантикой, эквивалентной параметрам вызова методов в языках программирования.

request-header = Accept                   ; Раздел 14.1
               | Accept-Charset           ; Раздел 14.2
               | Accept-Encoding          ; Раздел 14.3
               | Accept-Language          ; Раздел 14.4
               | Authorization            ; Раздел 14.8
               | From                     ; Раздел 14.22
               | Host                     ; Раздел 14.23
               | If-Modified-Since        ; Раздел 14.24
               | If-Match                 ; Раздел 14.25
               | If-None-Match            ; Раздел 14.26
               | If-Range                 ; Раздел 14.27
               | If-Unmodified-Since      ; Раздел 14.28
               | Max-Forwards             ; Раздел 14.31
               | Proxy-Authorization      ; Раздел 14.34
               | Range                    ; Раздел 14.36
               | Referer                  ; Раздел 14.37
               | User-Agent               ; Раздел 14.42

Имена полей заголовка запроса (Request-header) могут быть надежно расширены только в сочетании с изменением версии протокола. Однако, новые или экспериментальные поля заголовка могут получить семантику полей заголовка запроса (Request-header), если все стороны соединения распознают их как поля заголовка запроса (Request-header). Нераспознанные поля заголовка обрабатываются как поля заголовка объекта (entity-header).

6. Ответ (Response)

После получения и интерпретации сообщения запроса, сервер отвечает сообщением HTTP ответа.

Response      = Status-Line               ; Раздел 6.1
                *( general-header         ; Раздел 4.5
                 | response-header        ; Раздел 6.2
                 | entity-header )        ; Раздел 7.1
                CRLF
                [ message-body ]          ; Раздел 7.2

6.1 Строка состояния (Status-Line)

Первая строка ответа — это строка состояния (Status-Line). Она состоит из версии протокола (HTTP-Version), числового кода состояния (Status-Code) и поясняющей фразы (Reason-Phrase), разделенных символами SP. CR и LF не допустимы в Status-Line, за исключением конечной последовательности CRLF.

Status-Line = HTTP-Version SP Status-Code SP Reason-Phrase CRLF

6.1.1 Код состояния и поясняющая фраза

Элемент код состояния (Status-Code) — это целочисленный трехразрядный код результата понимания и удовлетворения запроса. Эти коды полностью определены в разделе 10. Поясняющая фраза (Reason-Phrase) предназначена для короткого текстового описания кода состояния. Код состояния (Status-Code) предназначен для использования автоматами, а поясняющая фраза предназначена для живых пользователей. От клиента не требуется исследовать или отображать поясняющую фразу (Reason-Phrase).

Первая цифра кода состояния определяет класс ответа. Последние две цифры не имеют определенной роли в классификации. Имеется 5 значений первой цифры:

Конкретные значения числовых кодов состояния, определенных в HTTP/1.1, и примерный набор соответствующих поясняющих фраз (Reason-Phrase) приводятся ниже. Поясняющие фразы (Reason-Phrase), перечисленные здесь являются рекомендуемыми, но могут быть заменены на эквивалентные без воздействия на протокол.

Status-Code    = "100"   ; Продолжать, Continue
               | "101"   ; Переключение протоколов,
                         ; Switching Protocols
               | "200"   ; OK
               | "201"   ; Создан, Created
               | "202"   ; Принято, Accepted
               | "203"   ; Не авторская информация,
                         ; Non-Authoritative Information
               | "204"   ; Нет содержимого, No Content
               | "205"   ; Сбросить содержимое, Reset
                         ; Content
               | "206"   ; Частичное содержимое, Partial
                         ; Content
               | "300"   ; Множественный выбор, Multiple
                         ; Choices
               | "301"   ; Постоянно перенесен, Moved
                         ; Permanently
               | "302"   ; Временно перемещен, Moved
                         ; Temporarily
               | "303"   ; Смотреть другой, See Other
               | "304"   ; Не модифицирован, Not Modified
               | "305"   ; Используйте прокси-сервер, Use
                         ; Proxy
               | "400"   ; Испорченный Запрос, Bad Request
               | "401"   ; Несанкционированно, Unauthorized
               | "402"   ; Требуется оплата, Payment
                         ; Required
               | "403"   ; Запрещено, Forbidden
               | "404"   ; Не найден, Not Found
               | "405"   ; Метод не дозволен, Method Not
                         ; Allowed
               | "406"   ; Не приемлем, Not Acceptable
               | "407"   ; Требуется установление
                         ; подлинности через прокси-сервер,
                         ; Proxy Authentication Required
               | "408"   ; Истекло время ожидания запроса,
                         ; Request Timeout
               | "409"   ; Конфликт, Conflict
               | "410"   ; Удален, Gone
               | "411"   ; Требуется длина, Length Required
               | "412"   ; Предусловие неверно,
                         ; Precondition Failed
               | "413"   ; Объект запроса слишком большой,
                         ; Request Entity Too Large
               | "414"   ; URI запроса слишком длинный,
                         ; Request-URI Too Long
               | "415"   ; Неподдерживаемый медиа тип,
                         ; Unsupported Media Type
               | "500"   ; Внутренняя ошибка сервера,
                         ; Internal Server Error
               | "501"   ; Не реализовано, Not Implemented
               | "502"   ; Ошибка шлюза, Bad Gateway
               | "503"   ; Сервис недоступен, Service
                         ; Unavailable
               | "504"   ; Истекло время ожидания от шлюза,
                         ; Gateway Timeout
               | "505"   ; Не поддерживаемая версия HTTP,
                         ; HTTP Version Not Supported
               | extension-code

extension-code = 3DIGIT

Reason-Phrase  = *<TEXT не включающий CR, LF>

Коды состояния HTTP расширяемы. HTTP приложениям не требуется понимать значение всех зарегистрированных кодов состояния, хотя такое понимание очень желательно. Однако, приложения ДОЛЖНЫ понимать класс любого кода состояния, который обозначается первой цифрой, и обрабатывать любой нераспознанный ответ как эквивалентный коду состояния x00 этого класса, за исключением тех случаев, когда нераспознанный ответ НЕ ДОЛЖЕН кэшироваться. Например, если клиентом получен и не был распознан код состояния 431, то он может безопасно считать, что в запросе что-то было неправильно и обрабатывать ответ, как если бы был получен код состояния 400. В таких случаях агентам пользователя СЛЕДУЕТ представить пользователю объект, возвращенный в ответе, так как этот объект, вероятно, включает читабельную для человека информацию, которая поясняет необычное состояние.

6.2 Поля заголовка ответа

Поля заголовка ответа (response-header fields) позволяют серверу передавать дополнительную информацию, касающуюся ответа, которая не может быть помещена в строку состояния Status-Line. Эти поля заголовка дают информацию о сервере и о дальнейшем доступе к ресурсу, указанному этим Request-URI.

response-header = Age                     ; Раздел 14.6
                | Location                ; Раздел 14.30
                | Proxy-Authenticate      ; Раздел 14.33
                | Public                  ; Раздел 14.35
                | Retry-After             ; Раздел 14.38
                | Server                  ; Раздел 14.39
                | Vary                    ; Раздел 14.43
                | Warning                 ; Раздел 14.45
                | WWW-Authenticate        ; Раздел 14.46

Имена полей заголовка ответа (Response-header) могут быть надежно расширены только в сочетании с изменением версии протокола. Однако, новые или экспериментальные поля заголовка могут получить семантику полей заголовка ответа (Response-header), если все стороны соединения распознают их как поля заголовка ответа (Response-header). Нераспознанные поля заголовка обрабатываются как поля заголовка объекта (entity-header).

Множество имен полей заголовка ответа (Response-header) может быть надежно расширено только в комбинации с изменением версии протокола. Однако, новые или экспериментальные поля заголовка с семантикой полей заголовка ответа МОГУТ быть добавлены если все участники соединения распознают их как поля заголовка ответа. Нераспознанные поля заголовка обрабатываются как поля заголовка объекта.

7. Объект (Entity)

Сообщения запросов и ответов МОГУТ передать объект, если иное не установлено методом запроса или кодом состояния ответа. Объект состоит из полей заголовка объекта (entity-header) и тела объекта (entity-body), хотя некоторые ответы могут включать только заголовки объекта (entity-headers).

Этот раздел относится как к отправителю, так и к получателю, то есть к клиенту или серверу, в зависимости от того, кто посылает, а кто получает объект.

7.1 Поля заголовка объекта

Поля заголовка объекта (Entity-header fields) определяют опциональную метаинформацию о теле объекта или, если тело не присутствует, относительно ресурса, идентифицированного запросом.

entity-header  = Allow                    ; Раздел 14.7
               | Content-Base             ; Раздел 14.11
               | Content-Encoding         ; Раздел 14.12
               | Content-Language         ; Раздел 14.13
               | Content-Length           ; Раздел 14.14
               | Content-Location         ; Раздел 14.15
               | Content-MD5              ; Раздел 14.16
               | Content-Range            ; Раздел 14.17
               | Content-Type             ; Раздел 14.18
               | ETag                     ; Раздел 14.20
               | Expires                  ; Раздел 14.21
               | Last-Modified            ; Раздел 14.29
               | extension-header

extension-header = message-header

Механизм расширения полей заголовка позволяет вводить дополнительные поля заголовка объекта (entity-header fields) не изменяя протокол, но эти поля не могут считаться распознаваемыми получателем. Нераспознанные поля заголовка получателю СЛЕДУЕТ игнорировать, а прокси-серверу пересылать без изменений.

7.2 Тело объекта

Тело объекта (если оно присутствует) посылается с HTTP запросом или ответом и имеет формат и кодирование, определяемое полями заголовка объекта (entity-header fields).

entity-body    = *OCTET

Тело объекта (entity-body) представлено в сообщении только тогда, когда присутствует тело сообщения (message-body), как описано в разделе 4.3. Тело объекта (entity-body) получается из тела сообщения (message-body), декодированием кодирования передачи, указанного в поле Transfer-Encoding, и которое может быть применено для гарантирования безопасной и правильной передачи сообщения.

7.2.1 Тип (Type)

Когда тело объекта (entity-body) включено в сообщение, тип данных этого тела определяется полями заголовка Content-Type и Content-Encoding. Они определяют двухуровневую упорядоченную модель кодирования:

entity-body := Content-Encoding( Content-Type( data ) )

Тип содержимого (Content-Type) определяет медиа тип основных данных. Кодирование содержимого (Content-Encoding) может использоваться для указания любого дополнительного кодирования содержимого, примененного к данным (обычно с целью сжатия данных). Кодирование содержимого (Content-Encoding) является свойством запрошенного ресурса. По умолчанию никакого кодирования не задано.

В любое HTTP/1.1 сообщение, содержащее тело объекта (entity-body) СЛЕДУЕТ включать поле заголовка Content-Type, определяющее медиа тип этого тела. В том и только в том случае, когда медиа тип не представлен полем Content-Type, получатель МОЖЕТ попытаться предположить медиа тип, проверяя содержимое и/или расширение (расширения) в имени URL, используемого для идентификации ресурса. Если медиа тип остался нераспознан, получателю СЛЕДУЕТ обрабатывать его как тип "application/octet-stream".

7.2.2 Длина (Length)

Длина тела объекта (entity-body) — это длина тела сообщения (message-body), полученного после декодирования всех кодирований передачи. Раздел 4.4 определяет как вычисляется длина тела сообщения (message-body).

8. Соединения (Connections)

8.1 Постоянные соединения (Persistent Connections)

8.1.1 Цель

До постоянных соединений для запроса каждого URL устанавливалось отдельное TCP соединение, что увеличивало нагрузку на HTTP сервера и вызывало загрузку Интернета. Использование встроенных изображений и других связанных данных часто требует от клиента делать несколько запросов к одному серверу за короткий промежуток времени. Исследования проблем эффективности такого решения доступны в [30][27]; анализ и результаты реализации прототипа находятся в [26].

Постоянные HTTP соединения имеют ряд преимуществ:

HTTP реализациям СЛЕДУЕТ реализовывать постоянные соединения.

8.1.2 Общее описание

Значительное отличие HTTP/1.1 от более ранних версий HTTP состоит в том, что постоянные соединения являются заданным по умолчанию поведением любого HTTP соединения. То есть если не обозначено иного, клиент может считать, что сервер поддержит постоянное соединение.

Постоянные соединения обеспечивают механизм, согласно которому клиент и сервер могут сообщить о разрыве TCP соединения. Это сигнализируется при помощи использования поля заголовка Connection. При получении сообщения о разрыве соединения клиент НЕ ДОЛЖЕН посылать больше запросов по этому соединению.

8.1.2.1 Обсуждение (Negotiation)

HTTP/1.1 сервер МОЖЕТ считать, что HTTP/1.1 клиент не предполагает поддерживать постоянное соединение, если посланный в запросе заголовок Connection содержит лексему соединения (connection-token) "close". Если сервер решает закрыть соединение немедленно после посылки ответа, то ему СЛЕДУЕТ послать заголовок Connection, который содержит лексему соединения (connection-token) "close".

HTTP/1.1 клиент МОЖЕТ ожидать, что соединение останется открытым, но должен решить оставлять ли его открытым на основании того, содержит ли ответ сервера заголовок Connection с лексемой соединения "close". В случае, если клиент не хочет поддерживать соединение для последующих запросов, ему СЛЕДУЕТ послать заголовок Connection, содержащий лексему соединения "close".

Если клиент или сервер посылает лексему закрытия соединения "close" в заголовке Connection, то запрос становится последним в соединении.

Клиентам и серверам НЕ СЛЕДУЕТ считать, что постоянное соединение поддерживается HTTP версиями, меньшими чем 1.1, если это не указано явно. Смотрите раздел 19.7.1 с более подробной информацией о обратной совместимости с HTTP/1.0 клиентами.

Чтобы соединение оставалось постоянным, все сообщения, передаваемые по нему должны иметь самоопределенную (self-defined) длину сообщения (то есть, не определяемую закрытием соединения), как описано в разделе 4.4.

8.1.2.2 Конвейерная обработка (Pipelining)

Клиент, который поддерживает постоянные соединения МОЖЕТ "произвести конвейерную обработку" запросов (то есть, посылать несколько запросов не ожидая ответа на каждый). Сервер ДОЛЖЕН послать ответы на эти запросы в том же самом порядке, в каком были получены запросы.

Клиенты, которые поддерживают постоянные соединения и производят конвейерную обработку немедленно после установления соединения, ДОЛЖНЫ быть готовы повторить соединение, если первая попытка конвейерной обработки дала сбой. Если клиент делает такой повтор, он НЕ ДОЛЖЕН производить конвейерную обработку прежде, чем узнает, что соединение постоянное. Клиенты ДОЛЖНЫ также быть готовы снова послать запросы, если сервер закрывает соединение перед посылкой всех соответствующих ответов.

8.1.3 Прокси-сервера (Proxy Servers)

Очень важно, чтобы прокси-сервера правильно выполняли свойства полей заголовка Connection, как определено в 14.2.1.

Прокси-сервер ДОЛЖЕН сообщать о постоянных соединениях отдельно своим клиентам и отдельно первоначальным серверам (или другим прокси-серверам), которые с ним соединены. Каждое постоянное соединение применяется только к одной транспортной связи.

Прокси-сервер НЕ ДОЛЖЕН устанавливать постоянное соединение с HTTP/1.0 клиентом.

8.1.4 Практические cоглашения (Practical Considerations)

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

Когда у клиента или сервера истекло время ожидания, ему СЛЕДУЕТ произвести изящное закрытие транспортного соединения. Как клиентам, так и серверам СЛЕДУЕТ постоянно наблюдать за другой стороной на предмет закрытия соединения, и соответственно отвечать. Если клиент или сервер не обнаруживает закрытия соединения другой стороной сразу, то это вызывает не оправданную трату ресурсов сети.

Клиент, сервер, или прокси-сервер МОГУТ закрыть транспортное соединение в любое время. Например, клиент МОЖЕТ начать посылать новый запрос в то время, когда сервер решает закрыть "бездействующее" соединение. С точки зрения сервера, соединение закрывается, в то время как оно было неактивно, но с точки зрения клиента, запрос произошел.

Это означает, что клиенты, серверы, и прокси-серверы ДОЛЖНЫ быть в состоянии обрабатывать асинхронные события закрытия. Программному обеспечению клиента СЛЕДУЕТ вновь открыть транспортное соединение и повторно передать прерванный запрос без взаимодействия с пользователем, поскольку метод запроса idempotent (смотрите раздел 9.1.2); другие методы НЕ ДОЛЖНЫ быть повторены автоматически, хотя агенты пользователя МОГУТ предложить оператору выбор повторять запрос, или нет.

Однако это автоматическое повторение НЕ СЛЕДУЕТ производить, если сбой происходит уже во втором запросе.

Серверам всегда СЛЕДУЕТ отвечать на по крайней мере на один запрос в соединении, если это возможно. Серверам НЕ СЛЕДУЕТ разрывать соединение в середине передачи ответа, если не предполагается сетевой или клиентский отказ.

Клиентам, использующим постоянные соединения, СЛЕДУЕТ ограничить число одновременных соединений, которые они устанавливают с данным сервером. Однопользовательскому клиенту СЛЕДУЕТ устанавливать максимум 2 соединения с любым сервером или прокси-сервером. Прокси-серверу СЛЕДУЕТ ограничиться 2*N соединеними с другими серверами или прокси-серверами, где N — число одновременно активных пользователей. Эти руководящие принципы предназначены для уменьшения времени HTTP ответа и избежания чрезмерной загрузки Интернета или других сетей.

8.2 Требования к передаче сообщений

Общие требования:

После получения метода, подчиненного этим требованиям, от HTTP/1.1 (или более позднего) клиента, HTTP/1.1 (или более поздний) сервер ДОЛЖЕН либо ответить кодом состояния 100 (Продолжать, Continue) и продолжать чтение входного потока, либо ответить ошибочным кодом состояния. Если сервер ответил ошибочным кодом состояния, то он МОЖЕТ либо закрыть транспортное соединение (TCP), либо продолжать читать и отбрасывать оставшуюся часть запроса. Он НЕ ДОЛЖЕН выполнять запрошенный метод, если возвратил код состояния ошибки.

Клиентам СЛЕДУЕТ помнить номер версии HTTP, используемой сервером по крайней мере в последний раз; если HTTP/1.1 клиент встречал HTTP/1.1 или более поздний ответ от сервера, и видит закрытие соединения перед получением какого-либо кода состояния от сервера, клиенту СЛЕДУЕТ повторить запрос без взаимодействия с пользователем, поскольку метод запроса idempotent (смотрите раздел 9.1.2); другие методы НЕ ДОЛЖНЫ быть повторены автоматически, хотя агенты пользователя МОГУТ предложить оператору выбор повторять запрос, или нет. Если клиент повторяет запрос, то он

Если HTTP/1.1 клиент не встречал ответа сервера версии HTTP/1.1 или более поздней, то ему следует считать, что сервер реализует HTTP/1.0 или более старый протокол и не использовать ответы с кодом состояния 100 (Продолжать, Continue). Если в такой ситуации клиент видит закрытие соединения перед получением какого-либо ответа с кодом состояния от сервера, то ему СЛЕДУЕТ повторить запрос. Если клиент повторяет запрос к этому HTTP/1.0 серверу, то он должен использовать следующий "binary exponential backoff" алгоритм, чтобы быть уверенным в получении надежного ответа:

  1. Инициализировать новое соединение с сервером.
  2. Передать заголовки запроса (request-headers).
  3. Инициализировать переменную R примерным временем передачи информации на сервер и обратно (например на основании времени установления соединения), или постоянным значение в 5 секунд, если время передачи не доступно.
  4. Вычислить T = R * (2**N), где N — число предыдущих повторов этого запроса.
  5. Либо дождаться от сервера ответа с кодом ошибки, либо просто выждать T секунд (смотря что произойдет раньше).
  6. Если ответа с кодом ошибки не получено, после T секунд передать тело запроса.
  7. Если клиент обнаруживает, что соединение было закрыто преждевременно, то ему нужно повторять начиная с шага 1, пока запрос не будет принят, либо пока не будет получен ошибочный ответ, либо пока у пользователя не кончится терпение и он не завершит процесс повторения.

Независимо от того, какая версия HTTP реализована сервером, если клиент получает ошибочный код состояния, то он

HTTP/1.1 (или более позднему) клиенту, который обнаруживает закрытие соединения после получения ответа с кодом состояния 100 (Продолжать, Continue), но до получения ответа с другим кодом состояния, СЛЕДУЕТ повторить запрос, но уже не ожидать ответа с кодом состояния 100 (Продолжать, Continue) (но он МОЖЕТ сделать так, если это упрощает реализацию).

9. Определения методов (Method Definitions)

Набор общих методов для HTTP/1.1 приводится ниже. Хотя этот набор может быть расширен, нельзя считать, что дополнительные методы имеют одиннаковую семантику, если они являются расширениями разных клиентов и серверов.

Поле заголовка запроса Host (раздел 14.23) ДОЛЖНО сопровождать все HTTP/1.1 запросы.

9.1 Безопасные и Idempotent методы

9.1.1 Безопасные методы

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

В частности было принято соглашение, что методы GET и HEAD никогда не должны иметь иного значения, кроме загрузки. Эти методы следует рассматривать как "безопасные". Это позволяет агентам пользователя представлять другие методы, такие как POST, PUT и DELETE, таким образом, чтобы пользователь был проинформирован о том, что он запрашивает выполнение потенциально опасного действия.

Естественно, не возможно гарантировать, что сервер не генерирует побочные эффекты в результате выполнения запроса GET; фактически, некоторые динамические ресурсы содержат такую возможность. Важное различие здесь в том, что не пользователь запрашивает побочные эффекты, и, следовательно, пользователь не может нести ответственность за них.

9.1.2 Idempotent методы

Методы могут также обладать свойством "idempotence" в том смысле, что побочные эффекты от N > 0 идентичных запросов такие же, как от одиночного запроса (за исключение ошибок и проблем устаревания). Методы GET, HEAD, PUT и DELETE обладают данным свойством.

9.2 OPTIONS

Метод OPTIONS представляет запрос информации об опциях соединения, доступных в цепочке запросов/ответов, идентифицируемой запрашиваемым URI (Request-URI). Этот метод позволяет клиенту определять опции и/или требования, связанные с ресурсом, или возможностями сервера, но не производя никаких действий над ресурсом и не инициируя его загрузку.

Если ответ сервера — это не сообщение об ошибке, то ответ НЕ ДОЛЖЕН содержать иной информации объекта, кроме той, которую можно рассматривать как опции соединения (например Allow — можно рассматривать как опцию соединения, а Content-Type — нет). Ответы на этот метод не кэшируются.

Если запрашиваемый URI (Request-URI) — звездочка ("*"), то запрос OPTIONS предназначен для обращения к серверу в целом. Если код состояния в ответе — 200, то ответу СЛЕДУЕТ содержать любые поля заголовка, которые указывают опциональные возможности, реализуемые сервером (например, Public), включая любые расширения, не определенные данной спецификацией, в дополнение к соответствующим общим полям или полям заголовка ответа (response-header). Как описано в разделе 5.1.2, запрос "OPTIONS *" может быть применен через прокси-сервер с определением адресуемого сервера в запрашиваемом URI (Request-URI) с пустым путем.

Если запрашиваемый URI (Request-URI) не звездочка ("*"), то запрос OPTIONS применяется к опциям, которые доступны при соединении с указанным ресурсом. Если код состояния ответа — 200, то ответу СЛЕДУЕТ содержать любые поля заголовка, которые указывают опциональные возможности, реализуемые сервером и применимые к указанному ресурсу (например, Allow), включая любые расширения, не определенные данной спецификацией, в дополнение к соответствующим общим полям или полям заголовка ответа (response-header). Если запрос OPTIONS передается через прокси-сервер, то последний редактирует ответ, исключая те опции, которые не предусмотрены возможности этого прокси-сервера.

9.3 GET

Метод GET позволяет получать любую информацию (в форме объекта), идентифицированную запрашиваемым URI (Request-URI). Если запрашиваемый URI (Request-URI) обращается к процессу, производящему данные, то в качестве объекта ответа должны быть возвращены произведенные данные, а не исходный текст процесса, если сам процесс не выводит исходный текст.

Различается "условный GET" ("conditional GET"), при котором сообщение запроса включает поля заголовка If-Modified-Since, If-Unmodified-Since, If-Match, If-None-Match, или If-Range. Условный метод GET запрашивает передачу объекта, только если он удовлетворяет условиям, описанным в условных полях заголовка. Условный метод GET предназначен для уменьшения ненужной загрузки сети, и позволяет обновлять кэшированные объекты без использования нескольких запросов или пересылки данных, уже сохраненных клиентом.

Различается также "частичный GET" ("partial GET"), при котором сообщение запроса включает поле заголовка Range. Частичный GET запрашивает передачу только части объекта, как описано в разделе 14.36. Частичный метод GET предназначен для уменьшения ненужной загрузки сети, и позволяет собирать объекты из частей, без передачи частей данных, уже сохраненных клиентом.

Ответ на запрос GET кэшируем тогда и только тогда, когда он отвечает требованиям HTTP кэширования, описанным в разделе 13.

9.4 HEAD

Метод HEAD идентичен GET, за исключением того, что сервер НЕ ДОЛЖЕН возвращать в ответе тело сообщения (message-body). Метаинформации, содержащейся в HTTP заголовках ответа на запрос HEAD СЛЕДУЕТ быть идентичной информации, представляемой в ответ на запрос GET. Этот метод может использоваться для получения метаинформации об объекте запроса без непосредственной пересылки тела объекта (entity-body). Этот метод часто используется для тестирования гипертекстовых связей в целях проверки правильности, достижимости, и времени модификации.

Ответ на запрос HEAD может быть кэшируемым в том смысле, что информация, содержащаяся в ответе может использоваться для модифицикации предварительно кэшированного объекта из этого ресурса. Если новые значения поля указывают, что кэшируемый объект отличается от текущего объекта (по таким параметрам, как Content-Length, Content-MD5, ETag или Last-Modified), то кэш ДОЛЖЕН обрабатывать содержимое как просроченное.

9.5 POST

Метод POST используется для запроса, при котором адресуемый сервер принимает объект, включенный в запрос, как новое подчинение ресурса, идентифицированного запрашиваемым URI (Request-URI) в строке запроса (Request-Line). POST разработан для того, чтобы общим методом реализовать следующие функции:

Фактически функция, выполняемая методом POST, определяется сервером и обычно зависит от запрашиваемого URI (Request-URI). Объект, передаваемый методом POST, относится к этому URI таким же образом, как файл относится к каталогу, в котором он находится, статья относится к конференции новостей (newsgroup), в которой она зарегистрирована, а запись относится к базе данных.

Действие, выполняемое методом POST может не давать в качестве результата ресурс, который можно было бы идентифицировать URI. В этом случае, в зависимости от того, включает ли ответ объект, описывающий результат, или нет, код состояния в ответе может быть как 200 (OK), так и 204 (Нет содержимого, No Content).

Если ресурс был создан на первоначальном сервере, ответу СЛЕДУЕТ содержать код состояния 201 (Создан, Created) и включать объект, который описывает состояние запроса и ссылается на новый ресурс, а также заголовок Location (смотрите раздел 14.30).

Ответы на этот метод не кэшируемы, если ответ не включает соответствующие поля заголовка Cache-Control или Expires. Однако, ответ с кодом состояния 303 (Смотреть другой, See Other) может использоваться для перенаправления агента пользователя для загрузки кэшируемого ресурса.

Запросы POST должны отвечать требованиям передачи сообщения, изложенным в разделе 8.2.

9.6 PUT

Запросы с методом PUT, которые содержат объект, сохраняются под запрашиваемым URI (Request-URI). Если Request-URI обращается к уже существующему ресурсу, включенный объект СЛЕДУЕТ рассматривать как модифицированную версию объекта, находящегося на первоначальном сервере. Если Request-URI не указывает на существующий ресурс, и может интерпретироваться агентом пользователя как новый ресурс для запросов, первоначальный сервер может создать ресурс с данным URI. Если новый ресурс создан, то первоначальный сервер ДОЛЖЕН сообщить агенту пользователя об этом посредством ответа с кодом состояния 201 (Создан, Created). Если существующий ресурс модифицирован, то для указания успешного завершения запроса СЛЕДУЕТ послать ответ с кодом состояния либо 200 (OK), либо 204 (Нет содержимого, No Content). Если ресурс не может быть создан или изменен для запрашиваемого URI (Request-URI), то СЛЕДУЕТ послать ответ, отражающий характер проблемы. Получатель объекта НЕ ДОЛЖЕН игнорировать заголовков Content-* (например Content-Range), которых не понимает или не реализует, а ДОЛЖЕН в данном случае возвратить ответ с кодом состояния 501 (Не реализовано, Not Implemented).

Если запрос передается через кэш и запрашиваемый URI (Request-URI) идентифицирует один или несколько кэшированных в настоящее время объектов, то вхождения в кэш этих объектов должны обрабатываться как просроченные. Ответы на этот метод не кэшируемы.

Фундаментальное различие между POST и PUT запросами, отражено в различном значении запрашиваемого URI (Request-URI). URI в запросе POST идентифицирует ресурс, который обрабатывает включенный объект. Этим ресурсом может быть процесс, принимающий данные, шлюз к некоторому другому протоколу, или отдельный объект, который принимает аннотации (accepts annotations). Напротив, URI в запросе PUT идентифицирует объект, включенный в запрос — агент пользователя назначает данный URI включенному ресурсу, а сервер НЕ ДОЛЖЕН пытаться применить запрос к некоторому другому ресурсу. Если сервер желает применить запрос к другому URI, он ДОЛЖЕН послать ответ с кодом 301 (Перемещен постоянно, Moved Permanently); агент пользователя МОЖЕТ затем принять собственное решение относительно переназначения запроса.

Одиночный ресурс МОЖЕТ быть идентифицирован несколькими различными URI. Например, статья может иметь URI идентифицирующий "текущую версию", который отличен от URI, идентифицирующего каждую специфическую версию. В этом случае, запрос PUT на общий URI может отразиться (may result) на нескольких других URI, определенных сервером происхождения.

HTTP/1.1 не определяет каким образом метод PUT воздействует на состояние первоначального сервера.

Запросы PUT должны подчиняться требованиям передачи сообщений, изложенным в разделе 8.2.

9.7 DELETE

Метод DELETE запрашивает первоначальный сервер об удалении ресурса, идентифицируемого запрашиваемым URI (Request-URI). Этот метод МОЖЕТ быть отменен человеческим вмешательством (или другими средствами) на первоначальном сервере. Клиенту нельзя гарантировать, что операция была выполнена, даже если код состояния, возвращенный первоначальным сервером указывает на то, что действие было завершено успешно. Однако, серверу НЕ СЛЕДУЕТ отвечать об успешном выполнении, если во время ответа он предполагает удалить ресурс или переместить его в недоступное положение.

Успешному ответу СЛЕДУЕТ иметь код состояния 200 (OK), если ответ включает объект, описывающий состояние, либо иметь код состояния 202 (Принято, Accepted), если действие еще не было произведено, либо иметь код состояния 204 (Нет содержимого, No Content), если ответ сообщает об успехе (OK), но не содержит объекта.

Если запрос передается через кэш и запрашиваемый URI (Request-URI) идентифицирует один или несколько кэшированных в настоящее время объектов, то вхождения их должны обрабатываться как просроченные. Ответы на этот метод не кэшируемы.

9.8 TRACE

Метод TRACE используется для вызова удаленного возврата сообщения запроса на уровне приложения. Конечному получателю запроса СЛЕДУЕТ отразить полученное сообщение обратно клиенту как тело объекта ответа с кодом состояния 200 (OK). Конечным получателем является либо сервер происхождения, либо первый прокси-сервер, либо первый шлюз, получивший нулевое значение (0) в поле Max-Forwards в запросе (см. раздел 14.31). Запрос TRACE НЕ ДОЛЖЕН содержать объекта.

TRACE позволяет клиенту видеть, что получается на другом конце цепочки запросов и использовать эти данные для тестирования или диагностической информации. Значение поля заголовка Via (раздел 14.44) представляет особый интерес, так как оно действует как след цепочки запросов. Использование поля заголовка Max-Forwards позволяет клиенту ограничивать длину цепочки запросов, что является полезным при тестировании бесконечных циклов в цепочке прокси-серверов, пересылающих сообщения.

Если запрос успешно выполнен, то ответу СЛЕДУЕТ содержать все сообщение запроса в теле объекта (entity-body), а Content-Type следует быть равным "message/http". Ответы на этот метод НЕ ДОЛЖНЫ кэшироваться.

10. Описания кодов состояния (Status Code Definitions)

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

10.1 1xx — Информационные коды

Этот класс кодов состояния указывает предварительный (временный) ответ, состоящий только из строки состояния (Status-Line) и опциональных заголовков, и завершающийся пустой строкой. Так как HTTP/1.0 не определял никаких 1xx кодов состояния, серверы НЕ ДОЛЖНЫ посылать 1xx ответы HTTP/1.0 клиентам, за исключением экспериментальных условий.

10.1.1 100 Продолжать, Continue

Клиент может продолжать запрос. Этот промежуточный ответ используется, для того, чтобы сообщить клиенту, что начальная часть запроса была получена и еще не отвергнута сервером. Клиенту СЛЕДУЕТ продолжить посылку оставшихся данных запроса или, если запрос уже был выполнен, игнорировать этот ответ. Сервер ДОЛЖЕН послать заключительный ответ после того, как запрос будет выполнен.

10.1.2 101 Переключение протоколов, Switching Protocols

Сервер понимает и желает выполнить запрос клиента, если протокол прикладной программы в этом соединении будет изменен на тот, который указан в поле заголовка сообщения Upgrade (раздел 14.41). Сервер переключит протокол на тот, который определен в поле заголовка ответа Upgrade непосредственно после пустой строки, которая завершает ответ с кодом состояния 101.

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

10.2 2xx — Успешные коды

Этот класс кодов состояния указывает, что запрос клиента был успешно получен, понят, и принят.

10.2.1 200 OK

Запрос был удачно выполнен. Информация, возвращаемая с ответом зависит от метода, используемого в запросе. Например:

GET   в ответе представлен объект, соответствующий запрошенному
      ресурсу;

HEAD  в ответе представлены поля заголовка объекта
      (entity-header), соответствующие запрошенному ресурсу. Тело
      сообщения (message-body) отсутствует;

POST  в ответе представлено описание объекта или содержится
      результат действия;

TRACE в ответе представлен объект, содержащий сообщение запроса,
      полученого конечным сервером.

10.2.2 201 Создан, Created

Запрос был выполнен и в результате был создан новый ресурс. Новый созданный ресурс может быть вызван по URI (одному или нескольким), возвращенным в объекте ответа; наиболее специфический URL для ресурса отдается в поле заголовка Location. Первоначальный сервер ДОЛЖЕН создать ресурс перед возвратом кода состояния 201. Если действие не может быть выполнено немедленно, сервер должен возвратить ответ с кодом состояния 202 (Принято, Accepted) вместо 201.

10.2.3 202 Принято, Accepted

Запрос был принят для обработки, но обработка не была завершена. В конечном счете запрос МОЖЕТ быть, а МОЖЕТ и не быть выполнен, поскольку он МОЖЕТ быть отвергнут при фактической обработке. Не имеется никакой возможности вторичной посылки кода состояния от асинхронной операции типа этой.

Ответ с кодом состояния 202 преднамеренно уклончив. Цель его состоит в том, чтобы позволить серверу принять запрос для некоторого другого процесса (возможно пакетно-ориентированного процесса, который выполняется только один раз в день) и не требовать при этом, чтобы соединение агента пользователя с сервером сохранялось до завершения процесса. Объекту, возвращенному с этим ответом СЛЕДУЕТ содержать индикатор текущего состояния запроса и либо ссылку на монитор состояния, либо некоторую оценку времени, когда пользователь может ожидать завершения выполнения запроса.

10.2.4 203 Не авторская информация, Non-Authoritative Information

Возвращенная в заголовке объекта (entity-header) метаинформация — это не оригинал, доступный на первоначальном сервере, а документ, собранный из локальных копий или копий третьей стороны. Представленный документ МОЖЕТ быть как подмножеством оригинальной версии, так и содержать сведения, которые в ней не были представлены. Например, включение локальной аннотирующей информацию о ресурсе МОЖЕТ расширить метаинформацию, известную первоначальному серверу. Использование этого кода состояния в ответе не является необходимым, но может применяться тогда, когда код состояния ответа отличен от 200 (OK).

10.2.5 204 Нет содержимого, No Content

Сервер выполнил запрос, но нет никакой новой информации, которую можно послать обратно. Если клиент — агент пользователя, ему НЕ СЛЕДУЕТ изменять вид документа, который послужил причиной запроса. Этот ответ предназначен прежде всего для того, чтобы позволить вводить данные для действий, не изменяя вид активного документа агента пользователя. Ответ МОЖЕТ включать новую метаинформацию в форме заголовков объекта (entity-headers), которые СЛЕДУЕТ добавить к документу, показываемому в настоящее время агентом пользователя.

Ответ с кодом состояния 204 НЕ ДОЛЖЕН содержать тела сообщения, и, таким образом, всегда завершается первой пустой строкой после полей заголовка.

10.2.6 205 Сбросить содержимое, Reset Content

Сервер выполнил запрос, и агенту пользователя СЛЕДУЕТ отменить просмотр документа, который инициировал запрос. Этот ответ предназначен прежде всего для того, чтобы позволить ввод данных, осуществляемый пользователем, с последующей очисткой формы, в которой сделан ввод, так, чтобы пользователь мог легко инициировать следующее действие ввода. Ответ НЕ ДОЛЖЕН содержать объект.

10.2.7 206 Частичное содержимое, Partial Content

Сервер выполнил частичный GET запрос ресурса. Запрос должен содержать поле заголовка Range (раздел 14.36), указывающее желаемый диапазон. Ответ ДОЛЖЕН содержать либо поле заголовка Content-Range (раздел 14.17), указывающее диапазон, включенный в ответ, либо тип содержимого (Content-Type) должен быть равным "multipart/byteranges", а поля Content-Range должны содержаться в каждой части. Если "multipart/byteranges" не используется, поле заголовка Content-Length в ответе ДОЛЖНО соответствовать фактическому числу октетов (OCTETs), переданных в теле сообщения (message-body).

Кэш, который не поддерживает заголовки Range и Content-Range НЕ ДОЛЖЕН кэшировать ответы с кодом состояния 206.

10.3 3xx — Перенаправление

Этот класс кодов состояния указывает, что для выполнения запроса агенту пользователя необходимо придпринять дополнительное действие. Требуемое действие МОЖЕТ быть выполнено агентом пользователя без взаимодействия с пользователем, тогда и только тогда, когда во втором запросе используется метод GET или HEAD. Агенту пользователя НЕ СЛЕДУЕТ автоматически перенаправлять запрос более 5 раз, так как такие переадресации обычно указывают бесконечный цикл.

10.3.1 300 Множественный выбор, Multiple Choices

Запрошенный ресурс имеет несколько представлений, и можно использовать любое из перечисленных. Каждое представление имеет свое расположение и информацию для агента по управлению диалогом (раздел 12), представленную таким образом, что пользователь (или агент пользователя) может выбрать наиболее подходящее представление и перенаправить запрос к нему.

Если запрос был отличен от HEAD, то ответу СЛЕДУЕТ содержать объект, включающий список характеристик и адресов, из которого пользователь или агент пользователя может выбрать один наиболее подходящий. Формат объекта определяется медиа типом, указанным в поле заголовка Content-Type. В зависимости от формата и возможностей агента пользователя, выбор наиболее подходящего представления может выполняться автоматически. Однако, эта спецификация не определяет какого-либо стандарта для автоматического выбора.

Если сервер имеет представление по умолчанию (наиболее предпочтительное), то ему СЛЕДУЕТ включить URL этого представления в поле Location; агенты пользователя МОГУТ использовать значение поля Location для автоматической переадресации. Этот ответ является кэшируемым, если не обозначено иного.

10.3.2 301 Постоянно перенесен, Moved Permanently

Запрошенному ресурсу был назначен новый постоянный URI, и любые будущие ссылки на этот ресурс СЛЕДУЕТ выполнять, используя один из возвращенных URI. Клиентам с возможностями редактирования связей СЛЕДУЕТ автоматически переопределить ссылки на запрашиваемый URI (Request-URI), используя одну или несколько новых ссылок, возвращенных сервером в тех местах, где это возможно. Этот ответ является кэшируемым, если не обозначено иного.

Если новый URI — это расположение, то ответу СЛЕДУЕТ содержать URL в поле Location. Если метод запроса был не HEAD, то объекту ответа СЛЕДУЕТ содержать короткое гипертекстовое примечание с гиперссылкой на новый (или новые) URI.

Если код состояния 301 был получен в ответ на запрос, отличный от GET или HEAD, агент пользователя НЕ ДОЛЖЕН автоматически переназначать запрос, пока нет подтверждения пользователя, так как иначе условия запроса изменятся.

Обратите внимание: При автоматическом переназначении запроса POST после получения кода состояния 301, некоторые существующие HTTP/1.0 агенты пользователя ошибочно изменят метод запроса на GET.

10.3.3 302 Временно перемещен, Moved Temporarily

Запрошенный ресурс временно находится под другим URI. Так как переадресация может быть изменена в любой момент, клиенту СЛЕДУЕТ продолжать использовать запрашиваемый URI (Request-URI) в будущих запросах. Кэшируемость этого ответа зависит только от содержимого полей заголовка Cache-Control или Expires (если этих полей нет, то ответ не кэшируется).

Если новый URI — это расположение, то ответу СЛЕДУЕТ содержать URL в поле Location. Если метод запроса был не HEAD, то объекту ответа СЛЕДУЕТ содержать короткое гипертекстовое примечание с гиперссылкой на новый (или новые) URI.

Если код состояния 302 был получен в ответ на запрос, отличный от GET или HEAD, агент пользователя НЕ ДОЛЖЕН автоматически переназначать запрос, пока нет подтверждения пользователя, так как иначе условия запроса изменятся.

Обратите внимание: При автоматическом переназначении запроса POST после получения кода состояния 302, некоторые существующие HTTP/1.0 агенты пользователя ошибочно изменят метод запроса на GET.

10.3.4 303 Смотреть другой, See Other

Ответ на запрос может быть найден под другим URI и его СЛЕДУЕТ запрашивать, используя метод GET для этого ресурса. Этот метод существует прежде всего для того, чтобы производить вывод данных активизированного методом POST сценария, используя перенаправление агента пользователя на указанный ресурс. Новый URI — это не ссылка, заменяющая первоначально запрошенный ресурс. Ответ с кодом состояния 303 не кэшируем, но ответ на второй (переназначенный) запрос МОЖЕТ быть кэширован.

Если новый URI — это расположение, то ответу СЛЕДУЕТ содержать URL в поле Location. Если метод запроса был не HEAD, то объекту ответа СЛЕДУЕТ содержать короткое гипертекстовое примечание с гиперссылкой на новый (или новые) URI.

10.3.5 304 Не модифицирован, Not Modified

Если клиент выполнил условный GET запрос, и доступ разрешен, но документ не изменился, то серверу СЛЕДУЕТ ответить, используя этот код состояния. Ответ НЕ ДОЛЖЕН содержать тела сообщения.

Ответ ДОЛЖЕН содержать следующие поля заголовка:

Если условный GET использует строгое сравнение кэша (strong cache validator) (смотреть раздел 13.3.3), ответу НЕ СЛЕДУЕТ содержать других заголовков объекта (entity-headers). Иначе (то есть, если условный GET использует слабое сравнение (weak validator)), ответ НЕ ДОЛЖЕН содержать других заголовков объекта; это предотвращает несогласованности между кэшированными телами объектов (entity-bodies) и модифицированными заголовками.

Если ответ с кодом состояния 304 указывает объект, в настоящее время не кэшированный, то кэш ДОЛЖЕН игнорировать ответ и повторить запрос без условного выражения.

Если кэш использует полученный ответ с кодом состояния 304 для модифицикации вхождения кэша, кэш ДОЛЖЕН модифицировать вхождение так, чтобы отразить любые новые значения полей, данные в ответе.

Ответ с кодом состояния 304 НЕ ДОЛЖЕН включать тела сообщения (message-body), и, таким образом, всегда завершается первой пустой строкой после полей заголовка.

10.3.6 305 Используйте прокси-сервер, Use Proxy

Обращение к запрошенному ресурсу ДОЛЖНО производиться через прокси-сервер, указанный в поле Location. В поле Location указан URL прокси-сервера. Ожидается, что получатель повторит запрос через прокси-сервер.

10.4 4xx — Коды ошибок клиента

Класс кодов состояния 4xx предназначен для случаев, когда клиент, возможно, допустил ошибку. За исключением ответа на запрос HEAD, серверу СЛЕДУЕТ включить объект, содержащий объяснение ошибочной ситуации, и объяснение, является ли она временной или постоянной. Эти коды состояния применимы к любому методу запроса. Агентам пользователя СЛЕДУЕТ показывать пользователю любой включенный объект.

Обратите внимание: Если клиент посылает данные, то реализации сервера, использующей TCP, следует гарантировать, что клиент подтвердил получение пакета(ов), содержащего ответ, прежде чем сервер закроет соединение. Если клиент продолжает посылать данные серверу после закрытия соединения, TCP стек сервера пошлет пакет сброса (RST) клиенту, а TCP стек клиента, в свою очередь, может стереть клиентские неподтвержденные входные буфера прежде, чем они будут прочитаны и интерпретированы приложением HTTP.

10.4.1 400 Испорченный Запрос, Bad Request

Запрос не может быть понят сервером из-за malformed синтаксиса. Клиенту НЕ СЛЕДУЕТ повторять запрос без модификаций.

10.4.2 401 Несанкционированно, Unauthorized

Запрос требует установления подлинности пользователя. Ответ ДОЛЖЕН включать поле заголовка WWW-Authenticate (раздел 14.46), содержащее вызов (challenge), применимый к запрошенному ресурсу. Клиент МОЖЕТ повторить запрос с подходящим полем заголовка Authorization (раздел 14.8). Если запрос уже включает рекомендации установления подлинности (Authorization credentials) в поле Authorization, то ответ с кодом состояния 401 указывает, что в установлении подлинности этим рекомендациям отказано. Если ответ с кодом состояния 401 содержит тот же самый вызов, что и предшествующий ответ, а агент пользователя уже делал попытку установления подлинности по крайней мере один раз, то СЛЕДУЕТ показать пользователю объект, который был дан в ответе, так как этот объект МОЖЕТ включать relevant диагностическую информацию. Установление подлинности доступа в протоколе HTTP описывается в разделе 11.

10.4.3 402 Требуется оплата, Payment Required

Этот код зарезервирован для будущего использования.

10.4.4 403 Запрещено, Forbidden

Сервер понял запрос, но отказывается выполнять его. Установление подлинности (Authorization) не поможет, и запрос НЕ ДОЛЖЕН быть повторен. Если метод запроса не HEAD и сервер желает указать, почему запрос не был выполнен, ему СЛЕДУЕТ описать причину отказа в объекте. Этот код состояния обычно используется, когда сервер не желает указывать точную причину отказа, или когда никакой другой ответ не подходит.

10.4.5 404 Не найден, Not Found

Сервер не нашел ничего, соответствующего данному запрашиваемому URI (Request-URI). Никак не сообщается является ли такое положение временным или постоянным.

Если сервер не желает делать данную информацию доступной клиенту, то вместо этого кода состояния может использоваться код состояния 403 (Запрещено, Forbidden). Код состояния 410 (Удален, Gone) СЛЕДУЕТ использовать, если сервер знает через некоторый внутренне конфигурируемый механизм, что старый ресурс более недоступен, но не знает нового адреса для пересылки.

10.4.6 405 Метод не дозволен, Method Not Allowed

Метод, определенный в строке запроса (Request-Line) не дозволено применять для ресурса, идентифицированного запрашиваемым URI (Request-URI). Ответ ДОЛЖЕН включать заголовок Allow, содержащий список допустимых методов для запрошенного ресурса.

10.4.7 406 Не приемлем, Not Acceptable

Ресурс, идентифицируемый запросом, имеет возможности генерации только таких объектов ответа, которые имеют характеристики содержимого (content characteristics), не согласующиеся с заголовками приема (accept headers), представленными в запросе.

Если это был не запрос HEAD, то в ответ СЛЕДУЕТ включить объект, содержащий список доступных характеристик объекта и адреса (locations), из которых пользователь или агент пользователя может выбрать наиболее подходящий. Формат объекта определеятся медиа типом, представленным в поле заголовка Content-Type. В зависимости от формата и возможностей агента пользователя, выбор наиболее подходящего варианта может выполняться автоматически. Однако, эта спецификация не определяет никакого стандарта для автоматического выбора.

Обратите внимание: HTTP/1.1 серверы позволяют возвращать ответы, которые не приемлемы согласно заголовкам приема (accept headers), представленным в запросе. В некоторых случаях, это может быть даже предпочтительно по сравнению с посылкой ответа с кодом состояния 406. Агентам пользователя неплохо бы рассматривать заголовки поступившего ответа, чтобы определить, является ли он приемлемым. Если ответ недопустим, агенту пользователя СЛЕДУЕТ временно остановиться, чтобы получить больше данных и спросить пользователя о дальнейших действиях.

10.4.8 407 Требуется установление подлинности через прокси-сервер,

Proxy Authentication Required.

Этот код подобен коду 401 (Несанкционированно, Unauthorized), но указывает, что клиент ДОЛЖЕН сначала установить свою подлинность (authenticate) прокси-серверу. Прокси-сервер ДОЛЖЕН возвратить поле заголовка Proxy-Authenticate (раздел 14.33), содержащее вызов (challenge), применяемый прокси-сервером для запрошенного ресурса. Клиент МОЖЕТ повторить запрос с подходящим полем заголовка Proxy-Authorization (раздел 14.34). Установление подлинности доступа в протоколе HTTP описывается в разделе 11.

10.4.9 408 Истекло время ожидания запроса, Request Timeout

Клиент не произвел запрос в течение времени, которое сервер готов ждать. Клиент МОЖЕТ повторить запрос без модификаций позже.

10.4.10 409 Конфликт, Conflict

Запрос не был выполнен из-за конфликта с текущим состоянием ресурса. Этот код позволяется только в ситуациях, когда ожидается, что пользователь может решить конфликт и повторно передать запрос. Телу ответа СЛЕДУЕТ содержать достаточное количество информации для пользователя, чтобы он мог распознать источник конфликта. В идеале, объект ответа должен включать достаточно информации для пользователя или агента пользователя для решения проблемы; однако это может не быть возможно, да и не требуется.

Конфликты, наиболее вероятно, будут возникать в ответ на запрос PUT. Если используется версификация, и объект, который должен быть помещен, включает изменения ресурса, которые находятся в противоречии со сделанными раньше каким-либо запросом (третьей стороны), сервер МОЖЕТ использовать ответ с кодом состояния 409, чтобы показать, что он не может выполнить запрос. В этом случае, объекту ответа СЛЕДУЕТ содержать список отличий двух версий в формате, определенном полем заголовка ответа Content-Type.

10.4.11 410 Удален, Gone

Запрошенный ресурс больше не доступен на сервере, и нет никакого адреса для перенаправления запроса. Такое состояние СЛЕДУЕТ рассматривать как постоянное. Клиентам с возможностями редактирования гиперсвязей СЛЕДУЕТ удалить ссылки на запрашиваемый URI (Request-URI) после одобрения пользователем. Если сервер не знает, или не может определить, является ли такое положение постоянным или нет, то ему СЛЕДУЕТ вместо этого кода использовать код состояния 404 (Не найден, Not Found). Этот ответ является кэшируемым, если не обозначено иного.

Ответ с кодом состояния 410 предназначен прежде всего для того, чтобы помочь в сопровождении WWW, уведомляя получателя, что ресурс преднамеренно недоступен и что владельцы сервера желают, чтобы удаленные связи, указывающие на этот ресурс были удалены. Такое случается в основном для ограниченных по времени, рекламных сервисов и для ресурсов, принадлежащих личностям, больше не занимающимся сайтом. Не обязательно отмечать все постоянно недоступные ресурсы как "удаленные" ("gone") или хранить запись в течение любого отрезка времени — это предоставляется на усмотрение владельца сервера.

10.4.12 411 Требуется длина, Length Required

Сервер отказывается принимать запрос с неопределенным Content-Length. Клиент МОЖЕТ повторить запрос, если добавит допустимое поле заголовка Content-Length, содержащее длину тела сообщения (message-body) в сообщении запроса.

10.4.13 412 Предусловие неверно, Precondition Failed

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

10.4.14 413 Объект запроса слишком большой, Request Entity Too Large

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

Если это временное состояние, то серверу СЛЕДУЕТ включить поле заголовка Retry-After для указания времени, через которое клиент может снова повторить запрос.

10.4.15 414 URI запроса слишком длинный, Request-URI Too Long

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

10.4.16 415 Неподдерживаемый медиа тип, Unsupported Media Type

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

10.5 5xx — Коды ошибок сервера

Коды состояния, начинающиеся с цифры "5" указывают случаи, в которых сервер знает, что допустил ошибку или неспособен выполнить запрос. Отвечая на запрос, за исключением запроса HEAD, серверу СЛЕДУЕТ включить объект, содержащий объяснение ошибочной ситуации и информацию, является ли это положение временным или постоянным. Агентам пользователя СЛЕДУЕТ показывать пользователю любой включенный объект. Эти коды состояния применимы к любому методу запроса.

10.5.1 500 Внутренняя ошибка сервера, Internal Server Error

Сервер столкнулся с непредвиденным условием, которое не позволяет ему выполнить запрос.

10.5.2 501 Не реализовано, Not Implemented

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

10.5.3 502 Ошибка шлюза, Bad Gateway

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

10.5.4 503 Сервис недоступен, Service Unavailable

Сервер в настоящее время не способен обработать запрос из-за временной перегрузки или обслуживания сервера. Это временное условие, которое будет облегчено после некоторой задержки. Если известна продолжительность задержки, она может быть указана в заголовке Retry-After. Если Retry-After не присутствует в ответе, клиенту СЛЕДУЕТ обрабатывать этот ответ как ответ с кодом 500.

Обратите внимание: существование кода состояния 503 не подразумевает, что сервер должен использовать его, когда перегружен. Некоторые сервера могут просто закрывать соединение.

10.5.5 504 Истекло время ожидания от шлюза, Gateway Timeout

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

10.5.6 505 Не поддерживаемая версия HTTP, HTTP Version Not Supported

Сервер не поддерживает, или отказывается поддерживать, версию HTTP протокола, которая используется в сообщении запроса. Сервер указывает, что не способен или не желает выполнять запрос, используя ту же самую major версию, что и клиент, как описано в разделе 3.1, в других сообщениях. Ответу СЛЕДУЕТ содержать объект, описывающий, почему эта версия не поддерживается, и какие другие протоколы поддерживаются этим сервером.

11. Установление подлинности доступа (Access Authentication)

HTTP обеспечивает для установления подлинности простой механизм вызов-ответ (challenge-response), который МОЖЕТ использоваться сервером для вызова (challenge) клиентского запроса, а клиентом для предоставления опознавательной информации (authentication information). Он использует расширяемую, не чувствительную к регистру лексему идентификации схемы установления подлинности (authentication scheme) и отделенный запятой список пар атрибут-значение (attribute-value), которые представляют параметры, необходимые для установления подлинности с использованием этой схемы.

auth-scheme    = token

auth-param     = token "=" quoted-string

Сообщение ответа с кодом 401 (Несанкционирован, Unauthorized) используется первоначальным сервером для вызова (challenge) установления подлинности (authorization) агентом пользователя. Этот ответ ДОЛЖЕН содержать поле заголовка WWW-Authenticate, включающее по крайней мере один вызов (challenge), применимый к запрошенному ресурсу.

challenge      = auth-scheme 1*SP realm *( "," auth-param )

realm          = "realm" "=" realm-value
realm-value    = quoted-string

Атрибут области (realm) (не чувствительный к регистру) требуется для всех схем установления подлинности, которые выдают вызов (challenge). Значение аттрибута realm (чувствительное к регистру), в комбинации с каноническим корневым URL (смотреть раздел 5.1.2) сервера, к которому обращен запрос, определяет область защиты (protection space). Эти области позволяют разбивать защищенные ресурсы сервера на множество областей, каждая из которых имеет собственную опознавательную схему и/или базу данных установления подлинности (authorization database). Значение realm — строка, вообще говоря назначенная первоначальным сервером, которая может иметь дополнительную семантику, специфическую для схемы установления подлинности (authentication scheme).

Агент пользователя, который хочет доказать свою подлинность серверу, обычно, но не обязательно, МОЖЕТ это сделать после получения ответа с кодом состояния 401 или 411, включив поле заголовка Authorization в запрос. Значение поля Authorization состоит из рекомендаций (credentials), содержащих информацию установления подлинности (authentication information) агента пользователя для области (realm) запрошенного ресурса.

credentials    = basic-credentials
               | auth-scheme #auth-param

Область (domain), над которой рекомендации (credentials) могут автоматически применяться агентом пользователя, определена областью защиты (protection space). Если подлинность была установлена предшествующим запросом, то эти же рекомендации (credentials) МОГУТ использоваться многократно во всех других запросах внутри этой области защиты (protection space) в течении времени, определенного схемой установления подлинности, параметрами, и/или установками пользователя. Если схемой установления подлинности не определено иного, то одиночная область защиты (protection space) не может простираться шире области сервера (the scope of its server).

Если сервер не желает принимать рекомендации (credentials), посланные в запросе, то ему СЛЕДУЕТ возвратить ответ с кодом 401 (Несанкционирован, Unauthorized). Ответ ДОЛЖЕН включать поле заголовка WWW-Authenticate, содержащее (возможно новый) вызов (challenge), применимый к запрошенному ресурсу, и объект, объясняющий отказ.

Протокол HTTP не ограничивает приложения использованием этого простого механизма вызов-ответ (challenge-response) для установления подлинности доступа. МОЖНО использовать дополнительные механизмы, такие как шифрование на транспортном уровне или формирование пакета сообщения (message encapsulation) с дополнительными полями заголовка, определяющими информацию установления подлинности. Однако эти дополнительные механизмы не определены в этой спецификации.

Прокси-сервера ДОЛЖНЫ быть полностью прозрачны для установления подлинности агента пользователя. То есть они ДОЛЖНЫ пересылать заголовки WWW-Authenticate и Authorization нетронутыми и следовать правилам раздела 14.8.

HTTP/1.1 позволяет клиенту передавать информацию установления подлинности для и от прокси-сервера посредством заголовков Proxy-Authenticate и Proxy-Authorization.

11.1 Базовая схема установления подлинности (Basic Authentication Scheme)

"Базовая" схема установления подлинности основана на том, что агент пользователя должен доказывать свою подлинность при помощи идентификатора пользователя (user-ID) и пароля (password) для каждой области (realm). Значению области (realm) следует быть непрозрачной (opaque) строкой, которую можно проверять только на равенство с другими областями на этом сервере. Сервер обслужит запрос, только если он может проверить правильность идентификатора пользователя (user-ID) и пароля (password) для защищенной области (protection space) запрошенного URI (Request-URI). Никаких опциональных опознавательных параметров нет.

После получения запроса на URI, находящийся в защищаемой области (protection space), сервер МОЖЕТ ответить вызовом (challenge), подобным следующему:

WWW-Authenticate: Basic realm="WallyWorld"

где "WallyWorld" — строка, назначенная сервером, которая идентифицирует область защиты запрашиваемого URI (Request-URI).

Чтобы получить права доступа, клиент посылает идентификатор пользователя (userid) и пароль (password), разделенные одним символом двоеточия (":"), внутри base64-кодированной строки рекомендаций (credentials).

basic-credentials = "Basic" SP basic-cookie

basic-cookie   = <base64-кодированный [7] user-pass,
                 за исключением не ограниченных 76
                 символами в строке>

user-pass   = userid ":" password

userid      = *<TEXT не содержащий ":">

password    = *TEXT

Userid может быть чувствителен к регистру.

Если агент пользователя хочет послать идентификатор пользователя (userid) "Aladdin", и пароль (password) "open sesame", он будет использовать следующее поле заголовка:

Authorization: Basic QWxhZGRpbjpvcGVuIHNlc2FtZQ==

Соглашения о защите, связанные с базовой схемой установления подлинности, смотрите в разделе 15.

11.2 Обзорная схема установления подлинности (Digest Authentication Scheme)

Обзорное установление подлинности для HTTP определяется в RFC 2069 [32].

12. Обсуждение содержимого (Content Negotiation)

Большинство HTTP ответов включают объект, который содержит информацию, предназначенную для интерпретации пользователем. Естественно желание обеспечить пользователя "лучшим доступным" объектом, соответствующим запросу. К сожалению для серверов и кэшей, не все пользователи имеют одиннаковые предпочтения, и не все агенты пользователя одинаково способны к визуализации всех типов объектов. По этой причине, HTTP имеет средства для нескольких механизмов "обсуждения содержимого" — процесса выбора самого лучшего представления для данного ответа, когда доступно несколько представлений.

Обратите внимание: Это не вызывается "обсуждение формата" ("format negotiation"), потому что альтернативные представления могут иметь одиннаковый медиа тип, но использовать различные возможности этого типа, иметь разные языки и т.д.

Любой ответ, содержащий тело объекта (entity-body) МОЖЕТ быть темой обсуждения, включая ошибочные ответы.

Имеются два вида обсуждения содержимого, которые возможны в HTTP: управляемое сервером и управляемое агентом обсуждение. Эти два вида обсуждения независимы, и, таким образом, могут использоваться отдельно или вместе. Один метод использования их вместе, упоминаемый как прозрачное обсуждение, происходит, когда кэш использует информацию обсуждения, управляемого агентом, предоставляя ее первоначальному серверу, для обеспечения управляемого сервером обсуждения при последующих запросах.

12.1 Управляемое сервером обсуждение

Обсуждение называется управляемым сервером, если выбор самого лучшего представления для ответа произведен алгоритмом, размещенным на сервере. Выбор основан на доступных представлениях ответа (они могут различаться по нескольким характеристикам; например языку, кодированию содержимого (content-coding), и т.д.) и содержании специфических полей заголовка в сообщении запроса, или на другой информации, имеющей отношение к запросу (такой как сетевой адрес клиента).

Управляемое сервером обсуждение выгодно, когда алгоритм выбора из числа доступных представлений трудно описать агенту пользователя, или когда сервер желает послать "лучшее предположение" клиенту одновременно с первым ответом (надеясь избежать задержки пересылки туда и обратно последующего запроса, если "лучшее предположение" устроит пользователя). Чтобы улучшить предположение сервера, агент пользователя МОЖЕТ включать поля заголовка запроса (Accept, Accept-Language, Accept-Encoding, и т.д.), которые описывают предпочтительный ответ.

Управляемое сервером обсуждение имеет недостатки:

  1. Сервер не может точно определить, что могло бы быть "самым лучшим" для данного пользователя, так как это требует полного знания, как возможностей агента пользователя, так и целей использования ответа (например, пользователь хочет просматривать его на экране или печатать на бумаге).
  2. Наличие описания возможностей агента пользователя в каждом запросе может быть очень неэффективным (при условии, что только небольшой процент ответов имеет несколько представлений) и потенциально нарушает секретность пользователя.
  3. Оно усложняет реализацию первоначального сервера и алгоритмов генерации ответов на запрос.
  4. Оно может ограничивать способность общего кэша использовать один и тот же ответ для запросов нескольких пользователей.

HTTP/1.1 включает следующие поля заголовка запроса (request-header), которые обеспечивают управляемое сервером обсуждение посредством описания возможностей агента пользователя и предпочтений самого пользователя: Accept (раздел 14.1), Accept-Charset (раздел 14.2), Accept-Encoding (раздел 14.3), Accept-Language (раздел 14.4), and User-Agent (раздел 14.42). Однако первоначальный сервер не ограничен этим и МОЖЕТ изменить ответ, основываясь на любом аспекте запроса, включая информацию, которая не содержится в полях заголовка запроса или информацию из расширенных полей заголовка, не определенных в этой спецификации.

Первоначальный сервер HTTP/1.1 ДОЛЖЕН включать соответствующее поле заголовка Vary (раздел 14.43) в любой кэшируемый ответ, основанный на управлямом сервером обсуждении. Поле заголовка Vary описывает характеристики, которые могут меняться в ответе (то есть характеристики, согласно которым первоначальный сервер выбирает "наилучший" ответ из нескольких представлений).

Общие HTTP/1.1 кэши ДОЛЖНЫ распознать поле заголовка Vary, если он присутствует в ответе, и отвечать требованиям, описанным в разделе 13.6, который описывает взаимодействия между кэшированием и обсуждением содержимого.

12.2 Управляемое агентом обсуждение

При управляемом агентом обсуждении, выбор лучшего представления ответа выполняется агентом пользователя после получения начального ответа первоначального сервера. Выбор основан на списке доступных представлений ответа, включенном в поля заголовка (эта спецификация резервирует имя поля Alternates, как описано в приложении 19.6.2.1) или тело объекта начального ответа. Каждое представление идентифицируется собственным URI. Выбор представления может выполняться автоматически (если агент пользователя способен это сделать) или вручную пользователем из сгенерированного (возможно гипертекстового) меню.

Управляемое агентом обсуждение выгодно, когда ответ варьируется по общеиспользуемым характеристикам (таким как тип, язык, или кодирование), когда первоначальный сервер не способен определить возможности агента пользователя путем исследования запроса, и обычно при использовании общих кэшей для распределения нагрузки на сервер и уменьшения использования сети.

Управляемое агентом обсуждение страдает тем, что для получения самого лучшего альтернативного представления требуется второй запрос. Этот второй запрос эффективен только тогда, когда используется кэширование. Кроме того, эта спецификация не определяет никакого механизма для обеспечения автоматического выбора, хотя также и не предотвращает разработку такого механизма в качестве расширения и использования в HTTP/1.1.

HTTP/1.1 определяет коды состояния 300 (Множественный выбор, Multiple Choices) и 406 (Не приемлем, Not Acceptable) для обеспечения управляемого агентом обсуждения, когда сервер не желает или не способен обеспечить изменение ответа, используя управляемое сервером обсуждение.

12.3 Прозрачное обсуждение

Прозрачное обсуждение — это комбинация управляемого сервером и управляемого агентом обсуждения. Когда кэш обеспечен списком доступных представлений ответа (как при управляемом агентом обсуждении) и изменяющиеся характеристики полностью поняты кэшем, тогда он способен выполнять управляемое сервером обсуждение последующих запросов этого же ресурса от имени первоначального сервера.

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

Эта спецификация не определяет никакого механизма прозрачного обсуждения, хотя также и не предотвращает разработку такого механизма в качестве расширения и использования в HTTP/1.1. HTTP/1.1 кэш, выполняющий прозрачное обсуждение ДОЛЖЕН включать поле заголовка Vary (определяющее параметры, которые могут варьироваться) в ответ, если он кэшируем, чтобы гарантировать правильную интерпретацию всеми HTTP/1.1 клиентами. Информацию управляемого агентом обсуждения, представленную первоначальным сервером, СЛЕДУЕТ включать в ответ при прозрачном обсуждении.

13. Кэширование в HTTP

HTTP обычно используется для распределенных информационных систем, где производительность может быть улучшена при помощи кэшей ответа. Протокол HTTP/1.1 включает многие элементы, предназначенные, чтобы сделать кэширующую работу, а также возможный. Поскольку эти элементы являются сложными от других аспектов протокола, и потому что они взаимодействуют с друг другом, полезно описать основной кэширующий дизайн HTTP отдельно от детализированных описаний методов, заголовков, кодов ответа, и т.д.

Кэширование было бы бесполезно, если бы оно значительно не улучшало производительность. Цель кэширования в HTTP/1.1 состоит в том, чтобы избавить от необходимости отправлять запросы во многих случаях, и избавлять от необходимости отправлять полные ответы во многих других случаях. Прежний сокращает количество сетевых круговых циклов, требуемых для многих операций; мы используем механизм "expiration" с этой целью (см. раздел 13.2). Последний уменьшает сетевые требования пропускной способности; мы используем механизм "проверки правильности" с этой целью (см. раздел 13.3).

Требования производительности, пригодности, и разъединенной операции требуют, чтобы мы были в состоянии ослабить цель семантической прозрачности. Протокол HTTP/1.1 позволяет серверам происхождения, кэшам, и клиентам явно уменьшать прозрачность когда необходимо. Однако, потому что непрозрачная операция может смутить пользователей неспециалиста, и может быть несовместимой с определенными приложениями — серверами (например, те для того, чтобы упорядочить товары), протокол требует, чтобы та прозрачность была ослаблена

Поэтому, протокол HTTP/1.1 предоставляет эти важные элементы:

  1. Возможности протокола, которые предоставляют полную семантическую прозрачность, когда это требуется всеми сторонами.
  2. Возможности протокола, которые позволяют серверу происхождения или user agent явно запрашивать и управлять непрозрачной операцией.
  3. Возможности протокола, которые позволяют кэшу прикреплять предупреждения ответам, которые не сохраняют запрошенное приближение семантической прозрачности.

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

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

13.1.1 Правильность кэширования

Правильный кэш ДОЛЖЕН ответить на запрос с самым современным ответом, хранившим кэшем, который является соответствующим запросу (см. разделы 13.2.5, 13.2.6, и 13.12), который удовлетворяет одному из следующих условий:

  1. Он был проверен для эквивалентности с тем, что сервер происхождения возвратит, повторно проверяя достоверность ответа с сервером происхождения (раздел 13.3);
  2. Он "достаточно нов" (см. раздел 13.2). В случае значения по умолчанию это означает, что он отвечает наименее ограничительному требованию свежести клиента, сервера, и кэша (см. раздел 14.9); если сервер происхождения так определяет, он — требование свежести сервера происхождения только.
  3. Он включает предупреждение, если запрос свежести клиента или сервера происхождения нарушен (см. раздел 13.1.5 и 14.45).
  4. Он — соответствующие 304 (Not Modified), 305 (Proxy Redirect), или ошибка (4xx или 5xx) ответное сообщение.

Если кэш не может поддержать связь с сервером происхождения, то правильный кэш ДОЛЖЕН ответить как выше, если ответ может быть правильно подан от кэша; если не он ДОЛЖЕН возвратить ошибку или предупреждение индикации, что был отказ взаимодействия.

Если бы кэш получает ответ (или весь ответ, или 304 (Not Modified) ответ), что он обычно отправлял бы клиенту запроса, и полученный ответ больше не нов, кэш ДОЛЖЕН отправить его клиенту запроса, не добавляя новый Warning (но не удаляя существующих заголовков Warning). Кэш не ДОЛЖЕН попытаться повторно проверить достоверность ответа просто, потому что тот ответ стал устарелым в пути; это могло бы привести к бесконечному циклу. user agent, который получает устарелый ответ без Warning, МОЖЕТ отобразить индикацию предупреждения пользователю.

13.1.2 Предупреждения

Всякий раз, когда кэш возвращает ответ, который не является ни непосредственно, ни "достаточно нов" (в смысле условия 2 в разделе 13.1.1), он должен прикрепить предупреждение тому эффекту, используя ответ Warning — заголовок. Это предупреждение позволяет клиентам предпринимать соответствующее действие.

Предупреждения могут использоваться в других целях, и связанных с кэшем и иначе. Использование предупреждения, а не код неисправности, отличает эти ответы от истинных отказов.

Предупреждения всегда cachable, потому что они никогда не ослабляют прозрачность ответа. Это означает, что предупреждения могут быть переданы к HTTP/1.0 кэши без опасности; такие кэши просто передадут предупреждение как заголовок объекта в ответе.

Предупреждения — назначенные числа между 0 и 99. Эта спецификация определяет номера кода, и значения каждого в настоящий момент назначали предупреждения, разрешая клиенту или кэшу предпринять автоматизированное действие в некоторых (но не все) случаи.

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

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

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

Заголовок Warning и в настоящий момент определенные предупреждения описаны в разделе 14.45.

13.1.3 Механизмы управления кэшем

Основные механизмы кэша в HTTP/1.1 (определенные сервером времена expiration и объекты для проверки правильности) являются неявными директивами к кэшам. В некоторых случаях, сервер или клиент, возможно, должны предоставить явные директивы кэшам HTTP. Мы используем заголовок Cache-Control с этой целью.

Заголовок Cache-Control позволяет клиенту или серверу передавать множество директив или в запросах или в ответах. Эти директивы обычно отменяют значение по умолчанию, кэширующее алгоритмы. Как правило, если есть какой-нибудь очевидный конфликт между значениями заголовка, самая ограничительная интерпретация должна быть применена (то есть, тот, который, наиболее вероятно, сохранит семантическую прозрачность). Однако, в некоторых случаях, директивы Cache-Control явно указаны как ослабление приближения семантической прозрачности (например, "max-stale" или "public").

Директивы Cache-Control описаны подробно в разделе 14.9.

13.1.4 Явные предупреждения User Agent

Много пользовательских агентов позволяют пользователям отменить основные кэширующие механизмы. Например, user agent может позволить пользователю определять, который кэшировал объекты (даже явно устарелые) никогда не утверждаются. Или user agent мог бы обычно добавлять "Cache-Control: max-stale =3600" к каждому запросу. Пользователю придется явно запросить или непрозрачное поведение, или поведение, которое заканчивается неправильно неэффективным кэшированием.

Если пользователь отменил основные кэширующие механизмы, user agent должен явно указать для пользователя всякий раз, когда это заканчивается дисплеем информации, которая не могла бы ответить требованиям прозрачности сервера (в частности если отображенный объект, как известно, является устарелым). Так как протокол обычно позволяет user agent определять, являются ли ответы устарелыми или нет, эта индикация должны только быть отображенными, когда это фактически случается. Индикация не диалоговое окно; он мог быть значок (например, изображение гниющей рыбы) или некоторый другой визуальный индикатор.

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

13.1.5 Исключения из правил и предупреждений

В некоторых случаях, оператор кэша может хотеть конфигурировать его, чтобы возвратить устарелые ответы даже когда не запрошенный клиентами. Это решение не должно быть принято слегка, но может быть необходимым по причинам пригодности или производительности, особенно когда кэш плохо подключен на сервер происхождения. Всякий раз, когда кэш возвращает устарелый ответ, он ДОЛЖЕН отметить его также (используя заголовок Warning). Это позволяет клиентскому программному обеспечению приводить пользователя в готовность, что может быть потенциальная проблема.

Он также позволяет user agent предпринимать шаги, чтобы получить непосредственный или новый ответ. Поэтому кэш не ДОЛЖЕН возвратить устарелый ответ, если клиент явно запрашивает непосредственный или новый, если не невозможно подчиниться для технического или причины политики.

13.1.6 Контроллируемое клиентом поведение

В то время как сервер происхождения (и до меньшей степени, промежуточных кэшей, их содействием возрасту ответа) является первичным источником информации expiration, в некоторых случаях клиент, возможно, должен управлять решением кэша о том, ли возвратить кэшируемый ответ, не проверяя достоверность его. Клиенты делают этот, используя несколько директив заголовка Cache-Control.

Запрос клиента может определить максимальный возраст, он желает к вводу неутвержденного ответа; определение нулевого значения вынуждает кэш (и) повторно проверить достоверность всех ответов. Клиент может также определить минимальное время, оставаясь прежде, чем ответ истечет. Обе из этих опций увеличивают ограничения на поведение кэшей, и так не могут далее ослабить приближение кэша семантической прозрачности.

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

13.2 Модель устаревания

13.2.1 Устаревание, определеяемое сервером

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

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

Механизм expiration применяется только к ответам, взятым от кэша а не к непосредственным ответам, отправленным немедленно клиенту запроса.

Если сервер происхождения желает вынудить семантически прозрачный кэш проверить достоверность каждого запроса, он может назначить явное время expiration в прошлом. Это означает, что ответ является всегда устарелым, и таким образом кэш ДОЛЖЕН проверить достоверность его перед использованием него для последующих запросов. См. раздел 14.9.4 для более ограничительного способа вызвать придание вновь юридической силы.

Если сервер происхождения желает вызвать какой-нибудь HTTP/1.1 кэш, независимо от того как он конфигурирован, проверить достоверность каждого запроса, он должен использовать "must-revalidate" директива Cache-Control (см. раздел 14.9).

Серверы определяют явные времена expiration или, используя заголовок Expires, или, используя директиву max-age заголовка Cache-Control.

Время expiration не может использоваться, чтобы вынудить user agent обновить свой дисплей или перезагрузить ресурс; его семантика применяется только к кэшированию механизмов, и такие механизмы должны только проверить состояние expiration ресурса, когда новый запрос на тот ресурс инициализирован. См. раздел 13.13 для объяснения различия между механизмами хронологии и кэшами.

13.2.2 Эвристическое устаревание

Так как серверы происхождения не всегда предоставляют явные времена expiration, кэши HTTP обычно назначают эвристические времена expiration, используя алгоритмы, которые используют другие значения заголовка (например, время Last-Modified), чтобы оценить вероятное время expiration. HTTP/1.1 спецификация не предоставляет специфичные алгоритмы, но действительно налагает ограничения самого плохого случая на их результаты. Так как эвристические времена expiration могут поставить под угрозу семантическую прозрачность, они должны использоваться осторожно, и мы поощряем серверы происхождения предоставлять явные времена expiration в максимально возможной степени.

13.2.3 Вычисление возраста

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

В этом обсуждении мы используем термин "теперь", чтобы означать "текущее значение часов в хосте, выполняющем вычисление." Хосты, которые используют HTTP, но особенно хосты, выполняющие серверы происхождения и кэши, должны использовать NTP [28] или некоторый подобный протокол, чтобы синхронизировать их часы к глобально точному стандарту времени.

Также отметьте, что HTTP/1.1 требует, чтобы серверы происхождения отправили заголовок Date с каждым ответом, давая время, в которое был сгенерирован ответ. Мы используем термин "date_value", чтобы обозначить значение заголовка Date, в форме, соответствующей арифметическим операциям.

HTTP/1.1 использует заголовок ответа Age, чтобы помочь передавать информацию о возрасте между кэшами. Значение заголовка Age — оценка отправителя количества времени, так как ответ был сгенерирован в сервере происхождения. В случае кэшируемого ответа, который был повторно утвержден с сервером происхождения, значение Age основано на времени придания вновь юридической силы, не оригинального ответа.

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

Мы используем термин "age_value", чтобы обозначить значение заголовка Age, в форме, соответствующей арифметическим операциям.

Возраст ответа может быть вычислен двумя полностью независимыми способами:

  1. теперь минус date_value, если локальные часы разумно хорошо синхронизированы на часы сервера происхождения. Если результат — негатив, результат заменен нулем.
  2. age_value, если все кэши вдоль пути ответа реализуют HTTP/1.1.

Учитывая, что у нас есть два независимых способа вычислить возраст ответа, когда он получен, мы можем объединить их как

corrected_received_age = max(now - date_value, age_value)

и пока мы или почти синхронизировали часы или все-HTTP/1.1 пути, каждый получает надежный (консервативный) результат.

Обратите внимание, что это исправление применен в каждом HTTP/1.1 кэш вдоль пути, так, чтобы, если есть HTTP/1.0 кэш в пути, правильный полученный возраст вычислен, пока часы кэша получения находятся почти в синхронизации. Мы не должны от начала до конца синхронизировать синхронизацию (хотя он хорош, чтобы иметь), и нет никакого явного шага синхронизации часов.

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

Поскольку запрос, который закончился возвращенным значением Age, должно быть, был инициализирован до той генерации значения Age, мы можем исправить для задержек, наложенных сетью, делая запись времени, в которое был инициализирован запрос. Затем, когда значение Age получено, оно ДОЛЖНО быть интерпретировано относительно времени, запрос был инициализирован, не время, когда ответ был получен. Этот алгоритм заканчивается консервативным поведением независимо от того, сколько задержки испытано. Так, мы вычисляем:

corrected_initial_age = corrected_received_age + (now - request_time)

где "request_time" — время (согласно локальным часам), когда запрос, который выявлял этот ответ, отправили.

Резюме алгоритма вычисления возраста, когда кэш получает ответ:

/*
 * age_value
 *      is the value of Age: header received by the cache with
 *              this response.
 * date_value
 *      is the value of the origin server's Date: header
 * request_time
 *      is the (local) time when the cache made the request
 *              that resulted in this cached response
 * response_time
 *      is the (local) time when the cache received the
 *              response
 * now
 *      is the current (local) time
 */
apparent_age = max(0, response_time - date_value);
corrected_received_age = max(apparent_age, age_value);
response_delay = response_time - request_time;
corrected_initial_age = corrected_received_age + response_delay;
resident_time = now - response_time;
current_age   = corrected_initial_age + resident_time;

Когда кэш отправляет ответ, он должен добавить к corrected_initial_age количество времени, что ответ был жителем локально. Он должен тогда передать этот полный возраст, используя заголовок Age, к следующему кэшу получателя.

Обратите внимание: То, что клиент не может надежно сказать, что ответ на собственном опыте — но присутствие заголовка Age указывает, что ответ определенно не непосредственно. Кроме того, если Date в ответе является более ранним чем локальное время запроса клиента, ответ вероятно не непосредственно (в отсутствии серьезной расфазировки тактовых сигналов).

13.2.4 Вычисление устаревания

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

Мы используем термин "expires_value", чтобы обозначить значение заголовка Expires. Мы используем термин "max_age_value", чтобы обозначить соответствующее значение числа секунд, несшего в соответствии с директивой max-age заголовка Cache-Control в ответе (см. раздел 14.10.

Директива max-age берет приоритет над Expires, так, если max-age присутствует в ответе, вычисление просто:

freshness_lifetime = max_age_value

Иначе, если Expires присутствует в ответе, вычисление:

freshness_lifetime = expires_value - date_value

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

Если ни Expires, ни Cache-Control: max-age появляется в ответе, и ответ не включает другие ограничения на кэширование, кэш МОЖЕТ вычислить время существования свежести, используя эвристику. Если значение больше чем 24 часа, кэш должен прикрепить Warning 13 к любому ответу, возраст которого составляет больше чем 24 часа, если такое предупреждение не было уже добавлено.

Кроме того, если у ответа действительно есть время Last-Modified, эвристическое значение expiration ДОЛЖНО быть не больше, чем некоторой фракцией интервала с этого времени. Типичная установка этой фракции могла бы составить 10 %.

Вычисление, чтобы определить, истек ли ответ, весьма просто:

response_is_fresh = (freshness_lifetime> current_age)

13.2.5 Значения однозначного устаревания

Поскольку значения expiration назначены оптимистично, он возможен для двух кэшей содержать новые значения для того же самого ресурса, которые отличны.

Если клиент, выполняющий поиск, получает ненепосредственный ответ для запроса, который был уже нов в его собственном кэше, и заголовок Date в его существующем элементе кэша более нов чем Date на новом ответе, то клиент МОЖЕТ проигнорировать ответ. Если так, он МОЖЕТ повторить запрос с "Cache-Control: max-age =0" директив (см. раздел 14.9), чтобы вызвать проверку с сервером происхождения.

Если у кэша есть два новых ответа для того же самого представления с другими объектами для проверки правильности, он ДОЛЖЕН использовать тот с более свежим заголовком Date. Эта ситуация может возникнуть, потому что кэш объединяет ответы от других кэшей, или потому что клиент попросил перезагрузку или придание вновь юридической силы очевидно нового элемента кэша.

13.2.6 Устранение неоднозначности Множественных Ответов

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

Ни тэг объекта, ни значение expiration не могут наложить упорядочение на ответы, так как он возможен, что более поздний ответ преднамеренно несет более раннее время expiration. Однако, HTTP/1.1 спецификация требует передачи заголовков Date на каждом ответе, и значения Date упорядочены степени детализации одной секунды.

Когда клиент пытается повторно проверить достоверность элемента кэша, и ответ, который он получает, содержит заголовок Date, который оказывается старший чем тот для существующего элемента, тогда клиент ДОЛЖЕН повторить запрос безоговорочно, и включить

Cache-Control: max-age =0

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

Cache-Control: no-cache

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

Если значения Date равны, то клиент может использовать или ответ (или, если он чрезвычайно благоразумен, может запросить новый ответ). Серверы не ДОЛЖНЫ зависеть у клиентов, являющихся способным выбрать deterministically между ответами, сгенерированными в течение той же самой секунды, если их времена expiration накладываются.

13.3 Модель сравнения (validation model)

Когда у кэша есть устарелый элемент, который он хотел бы использовать как ответ на запрос клиента, он сначала должен свериться с сервером происхождения (или возможно промежуточный кэш с новым ответом), чтобы видеть, пригоден ли его кэшируемый элемент все еще для использования. Мы вызываем эту "проверку достоверности" элемента кэша. Так как мы не хотим должными быть заплатить издержки перепередачи полного ответа, если кэшируемый элемент хорош, и мы не хотим заплатить издержки дополнительного цикла обработки, если кэшируемый элемент недопустим, протокол HTTP/1.1 поддерживает использование условных методов.

Ключевые возможности протокола поддержки условных методов являются теми "объектами для проверки правильности кэша, о которых беспокоятся." Когда сервер происхождения генерирует полный ответ, он прикрепляет своего рода объект для проверки правильности к нему, который сохранен с элементом кэша. Когда клиент (user agent или кэш прокси-сервера) делает условный запрос на ресурс, для которого у него есть элемент кэша, он включает связанный объект для проверки правильности в запрос.

Сервер тогда проверяет тот объект для проверки правильности против текущего объекта для проверки правильности для объекта, и, если они соответствуют, он отвечает специальным кодом состояния (обычно, 304 (Not Modified)) и никакое тело объекта. Иначе, он возвращает полный ответ (включение тела объекта). Таким образом, мы избегаем передавать полный ответ, если объект для проверки правильности соответствует, и мы избегаем дополнительного цикла обработки, если он не соответствует.

Обратите внимание: Функции сравнения, используемые, чтобы решить, соответствуют ли объекты для проверки правильности, определены в разделе 13.3.3.

В HTTP/1.1, условный запрос смотрит точно то же самое как нормальный запрос на тот же самый ресурс, за исключением того, что он несет специальный заголовок (который включает объект для проверки правильности), который неявно поворачивает метод (обычно, GET) в условное выражение.

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

Обратите внимание: Ответ, который испытывает недостаток в объекте для проверки правильности, может все еще кэшироваться, и подаваться от кэша, пока он не истекает, если это явно не запрещено в соответствии с директивой Cache-Control. Однако, кэш не может сделать условного поиска, если у него нет объекта для проверки правильности для объекта, который означает, что он не будет регенерируем после того, как он истечет.

13.3.1 Даты последнего изменения (Last-modified Dates)

Значение поля заголовка объекта Last-Modified часто используется как объект для проверки правильности кэша. В простых терминах элемент кэша рассматривается, чтобы быть правильным, если объект не был изменен начиная со значения Last-Modified.

13.3.2 Объектные отметки сравнения кэша

Значение поля заголовка объекта ETag, тэг объекта, предусматривает "непрозрачный" объект для проверки правильности кэша. Это может позволить более надежную проверку правильности в ситуациях, где он неудобен, чтобы хранить даты модификации, где одно-секундная разрешающая способность значений даты HTTP не достаточна, или где сервер происхождения желает избежать определенных парадоксов, которые могут явиться результатом использования дат модификации.

Тэгы Объекта описаны в разделе 3.11. Заголовки, используемые с тэгами объекта, описаны в разделах 14.20, 14.25, 14.26 и 14.43.

13.3.3 Слабое и сильное сравнение

И начиная с серверы происхождения и начиная с кэши сравнят два объекта для проверки правильности, чтобы решить, представляют ли они те же самые или другие объекты, обычно можно было бы ожидать это, если объект (тело объекта или любой объект — заголовки) изменения в любом случае, то связанный объект для проверки правильности изменится также. Если это истинно, то мы называем этот объект для проверки правильности "сильным объектом для проверки правильности."

Однако, могут быть случаи, когда сервер предпочитает изменять объект для проверки правильности только на семантически существенных изменениях, и не, когда незначащие аспекты объекта изменяются. Объект для проверки правильности, который не всегда изменяется, когда ресурс изменяется, является "слабым объектом для проверки правильности."

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

Обратите внимание: Один пример сильного объекта для проверки правильности — целое число, которое увеличено в устойчивой памяти каждый раз, когда объект изменен.

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

Поддержка слабых объектов для проверки правильности является опциональной; однако, слабые объекты для проверки правильности учитывают более эффективное кэширование эквивалентных объектов; например, счетчик посещений на сайте вероятно достаточно хорош, если он обновлен каждые несколько дней или недель, и любое значение в течение той точки вероятно "достаточно хорошее", чтобы быть эквивалентным.

"Использование" объекта для проверки правильности или когда клиент генерирует запрос и включает объект для проверки правильности в поле заголовка проверки достоверности, или когда сервер сравнивает два объекта для проверки правильности.

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

Единственная функция, которую протокол HTTP/1.1 определяет в объектах для проверки правильности, является сравнением. Есть две функции сравнения объекта для проверки правильности, в зависимости от того, позволяет ли контекст сравнения использование слабых объектов для проверки правильности или нет:

Слабая функция MAY сравнения использоваться для простого (неподдиапазон) запросы GET. Сильная функция MUST сравнения использоваться во всех других случаях.

Тэг объекта силен, если он явно не отмечен как слабый. Раздел 3.11 дает синтаксис для тэгов объекта.

Время Last-Modified, когда используется как объект для проверки правильности в запросе, неявно слабо, если он не возможен вывести, что он силен, используя следующие правила:

или

или

Этот метод полагается на факт, что, если два других ответа отправил сервер происхождения в течение той же самой секунды, но у обоих было то же самое время Last-Modified, то у по крайней мере одного из тех ответов будет значение Date равным его времени Last-Modified. Произвольные 60-вторых пределов принимают меры против возможности, что Date и Последний — значения Modified сгенерирован от других часов, или в несколько другие времена во время подготовки ответа. Реализация может использовать значение, большее чем 60 секунд, если полагается, что 60 секунд слишком коротки.

Если клиент желает выполнить поиск поддиапазона на значении, для которого у него есть только время Last-Modified и никакой непрозрачный объект для проверки правильности, он может сделать это, только если время Last-Modified сильно в смысле, описанном здесь.

Кэш или сервер происхождения, получающий запрос cache-conditional, кроме полного тела запрос GET, ДОЛЖНЫ использовать сильную функцию сравнения, чтобы оценить условие.

Эти правила позволяют HTTP/1.1 кэши и клиенты безопасно исполнять под — поиски диапазона на значениях, которые были получены из HTTP/1.0 серверы.

13.3.4 Правила когда использовать объектные отметки (Entity Tags) и даты последнего изменения (Last-modified Dates)

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

HTTP/1.1 серверы происхождения:

Другими словами, предпочтительное поведение для HTTP/1.1 сервер происхождения состоит в том, чтобы отправить и сильный тэг объекта и значение Last-Modified.

Чтобы быть юридическим, сильный тэг объекта ДОЛЖЕН измениться всякий раз, когда связанное значение объекта изменяется в любом случае. Слабый тэг объекта ДОЛЖЕН измениться всякий раз, когда связанный объект изменяется семантически существенным способом.

Обратите внимание: Чтобы предоставить семантически прозрачное кэширование, сервер происхождения должен избежать многократно использовать специфичное сильное значение тэга объекта для двух других объектов, или многократно использовать специфичное слабое значение тэга объекта для двух семантически других объектов. Входы кэша могут сохраниться в течение произвольно длительных периодов, независимо от времен expiration, таким образом может быть неуместно ожидать, что кэш никогда не будет снова пытаться проверить достоверность элемента, используя объект для проверки правильности, который он получил в некоторый момент в прошлом.

HTTP/1.1 клиенты:

HTTP/1.1 кэш, после получения запроса, ДОЛЖЕН использовать самый ограничительный объект для проверки правильности, решая, соответствует ли элемент кэша клиента собственному элементу кэша кэша. Это — только выпуск, когда запрос содержит и тэг объекта и объект для проверки правильности даты последнего изменения (If-Modified-Since или If-Unmodified-Since).

Примечание относительно объяснения: Общий принцип позади этих правил — то, что HTTP/1.1 серверы и клиенты должен передать так много безызбыточной информации, как доступно в их ответах и запросах. HTTP/1.1 системы, получающие эту информацию, сделает самые консервативные предположения об объектах для проверки правильности, которые они получают.

HTTP/1.0 клиенты и кэши проигнорирует тэгы объекта. Обычно, последним образом измененные значения, полученные или используемые этими системами, поддержат прозрачное и эффективное кэширование, и таким образом HTTP/1.1 серверы происхождения должен будет предоставить значения Last-Modified. В тех редких случаях, где использование значения Last-Modified, поскольку объект для проверки правильности HTTP/1.0 система мог закончиться серьезной проблемой, тогда HTTP/1.1 серверы происхождения не должен предоставить тот.

13.3.5 Непроверяемые условия

Принцип позади тэгов объекта — то, что только сервисный автор знает, что семантика ресурса достаточно хорошо выбирает соответствующий механизм проверки правильности кэша, и спецификацию любой более сложной функции сравнения объекта для проверки правильности, чем равенство байта открыло бы кучу проблем. Таким образом, сравнения любых других заголовков (кроме Last-Modified, для совместимости с HTTP/1.0) никогда не используются в целях проверить достоверность элемента кэша.

13.4 Cachability ответа

Если определенно не сдержано Cache-Control (раздел 14.9) директива, кэширующая система может всегда хранить успешный ответ (см. раздел 13.8) как элемент кэша, может возвратить его без проверки правильности, если он нов, и может возвратить его после успешной проверки правильности. Если нет ни объекта для проверки правильности кэша, ни явное время expiration, связанное с ответом, мы не ожидаем, что он будет кэшироваться, но определенные кэши могут нарушить это ожидание (например, когда немного или нисколько сетевого обеспечения связи доступно). Клиент может обычно обнаруживать тот такой ответ, был взят от кэша, сравнивая заголовок Date с текущим временем.

Обратите внимание: Тот некоторый HTTP/1.0 кэши, как известно, нарушает это ожидание, не предоставляя Warning.

Однако, в некоторых случаях может быть неуместно для кэша сохранить объект, или возвратить его в ответ на последующий запрос. Это может быть то, потому что абсолютную семантическую прозрачность считает необходимой сервисный автор, или из-за рассмотрений частной жизни или безопасности.

Определенные директивы Cache-Control поэтому предоставлены так, чтобы сервер мог указать, что определенные объекты ресурса, или части этого, не могут кэшироваться независимо от других рассмотрений.

Обратите внимание: Тот раздел 14.8 обычно препятствует тому, чтобы общедоступный кэш сохранил и возвратил ответ на предыдущий запрос, если тот запрос включал заголовок Authorization.

Ответ, полученный с кодом состояния 200, 203, 206, 300, 301 или 410, может быть сохранен кэшем и использоваться в ответ на последующий запрос, подчиненный механизму expiration, если директива Cache-Control не запрещает кэширование. Однако, кэш, который не поддерживает Range и заголовки Content-Range, не ДОЛЖЕН кэшировать 206 (Partial Content) ответы.

Ответ, полученный с любым другим кодом состояния, не ДОЛЖЕН быть возвращен в ответе на последующий запрос, если нет директивы Cache-Control или другой заголовок (ки), которые явно позволяют его. Например, они включают следующее: заголовок Expires (раздел 14.21); "max-age", "must-revalidate", "proxy-revalidate", "public" или "private" директива Cache-Control (раздел 14.9).

13.5 Построение ответов из кэшей

Цель кэша HTTP состоит в том, чтобы хранить информацию, полученную в ответ на запросы, для использования в отвечании на будущие запросы. Во многих случаях, кэш просто возвращает соответствующие части ответа на программу формирования запросов. Однако, если кэш хранит элемент кэша, основанный на предыдущем ответе, ему, вероятно, придется объединить части нового ответа с тем, что хранится в элементе кэша.

13.5.1 Сквозные (End-to-end) и промежуточные (Hop-by-hop) заголовки

С целью определения поведения кэшей и некэширования прокси, мы делим заголовки HTTP на две категории:

Следующий HTTP/1.1 заголовки является заголовками перелета перелетом:

Все другие заголовки, определенные HTTP/1.1, являются непрерывными заголовками.

Заголовки Hop-by-hop, введенные в будущих версиях HTTP, ДОЛЖНЫ быть перечислены в заголовке Connection, как описано в разделе 14.10.

13.5.2 Немодифицируемые заголовки

Некоторые возможности протокол HTTP/1.1, например, Digest Authentication, зависят от значения определенных непрерывных заголовков. Кэш или некэширующий прокси не ДОЛЖНЫ изменить непрерывный заголовок, если определение того заголовка не требует или определенно позволяет это.

Кэш или некэширующий прокси не ДОЛЖНЫ изменить ни одно из следующих полей в запросе или ответе, и при этом он уже не может добавить ни одно из этих полей если не существующий:

Кэш или некэширующий прокси не ДОЛЖНЫ изменить или добавить ни одно из следующих полей в ответе, который содержит no-transform директива CacheControl, или в любом запросе:

Кэш или некэширующий прокси МОГУТ изменить или добавить эти поля в ответе, который не включает no-transform, но если он делает так, он ДОЛЖЕН добавить Warning 14 (примененная Трансформация), если Вы уже не появляетесь в ответе.

Обратите внимание: Ненужная модификация непрерывных заголовков может вызвать опознавательные отказы, если более сильные опознавательные механизмы введены в более поздних версиях HTTP. Такие опознавательные механизмы могут положиться на значения полей заголовка, не перечисленных здесь.

13.5.3 Объединение заголовков

Когда кэш делает запрос проверки достоверности на сервер, и сервер предоставляет 304 (Not Modified) ответ, кэш должен создать ответ, чтобы отправить клиенту запроса. Кэш использует тело объекта, сохраненное в элементе кэша как тело объекта этого уходящего ответа. Непрерывные заголовки, сохраненные в элементе кэша, используются для созданного ответа, за исключением того, что любые непрерывные заголовки, предоставленные в 304 ответах, ДОЛЖНЫ заменить соответствующие заголовки от элемента кэша. Если кэш не решает удалять элемент кэша, он ДОЛЖЕН также заменить непрерывные заголовки, сохраненные элементом кэша с соответствующими заголовками, полученными во входящем ответе.

Другими словами, набор непрерывных заголовков, полученных во входящем ответе, отменяет все соответствующие непрерывные заголовки, сохраненные с элементом кэша. Кэш может добавить заголовки Warning (см. раздел 14.45) к этому набору.

Если заголовок, field-name во входящем ответе соответствует больше чем одному заголовку в элементе кэша, всем таким старым заголовкам, заменен.

Обратите внимание: Это правило позволяет серверу происхождения использовать 304 (Not Modified) ответ, чтобы обновить любой заголовок, связанный с предыдущим ответом для того же самого объекта, хотя он мог бы не всегда быть значим или исправлять, чтобы сделать так. Это правило не позволяет серверу происхождения использовать 304 (not Modified) ответ, чтобы полностью удалить заголовок, которому он предоставил предыдущий ответ.

13.5.4 Объединнение диапазонов байтов (Byte Ranges)

Ответ может передать только поддиапазон байтов entitybody, или потому что запрос включал одну или более спецификаций Range, или потому что подключение было прервано преждевременно. После нескольких таких передач кэш, возможно, получил несколько диапазонов того же самого тела объекта.

Если у кэша есть сохраненное непустое множество поддиапазонов для объекта, и входящий ответ передает другой поддиапазон, кэш МОЖЕТ объединить новый поддиапазон с существующим набором, если оба следующие условия встречены:

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

13.6 Кэширование переговорных ответов (Negotiated Responses)

Использование управляемых сервером переговоров контента (раздел 12), как обозначено присутствием поля заголовка Vary в ответе, изменяет условия и процедуру, которой кэш может использовать ответ для последующих запросов.

Сервер ДОЛЖЕН использовать поле заголовка Vary (раздел 14.43), чтобы сообщить кэшу того, что размерности поля заголовка используются, чтобы выбрать среди множественных представлений cachable ответа. Кэш может использовать выбранное представление (объект, включенный в тот определенный ответ) для того, чтобы ответить на последующие запросы на том ресурсе только, когда у последующих запросов есть те же самые или эквивалентные значения для всех полей заголовка, указанных в заголовке ответа Vary. Запросы с другим значением для один или больше тех полей заголовка были бы отправлены к серверу происхождения.

Если бы тэг объекта был назначен представлению, то отправленный запрос ДОЛЖЕН быть условным выражением и включить тэгы объекта в поле заголовка IfNone-соответствия от всех его входов кэша для RequestURI. Это передает серверу набор объектов, в настоящий момент хранивших кэшем, так, чтобы, если любой из этих объектов соответствует запрошенному объекту, сервер мог использовать заголовок ETag в его 304 (Not Modified) ответ, чтобы сказать кэш, какой элемент является соответствующим. Если entity-tag новых соответствий ответа тот из существующего элемента, новый ответ ДОЛЖЕН использоваться, чтобы обновить поля заголовка существующего элемента, и результат ДОЛЖЕН быть возвращен клиенту.

Поле заголовка Vary может также сообщить кэшу, что представление было выбрано, используя критерии, не ограниченные заголовками запроса; в этом случае, кэш не ДОЛЖЕН использовать ответ в ответе на последующий запрос, если кэш не передает новый запрос на сервер происхождения в условном запросе, и сервер отвечает 304 (Not Modified), включая тэг объекта или Content-Location, который указывает, какой объект должен использоваться.

Если любой из существующих входов кэша содержит только частичный контент для связанного объекта, его entity-tag не ДОЛЖЕН быть включен в заголовок If-None-Match, если запрос не для диапазона, которому полностью удовлетворил бы тот элемент.

Если кэш получает успешный ответ, соответствия поля Content-Location которого тот из существующего элемента кэша для того же самого RequestURI, entity-tag которого отличается от того из существующего элемента, и чей Date более свеж чем тот из существующего элемента, существующий элемент не ДОЛЖЕН быть возвращен в ответ на будущие запросы, и должен быть удален из кэша.

13.7 Общедоступные и необщедоступные кэши

По причинам безопасности и частной жизни, он необходим, чтобы сделать различие между "общедоступным" и кэши "non-shared". Кэш non-shared — тот, который доступен только для отдельного пользователя. Доступность в этом случае ДОЛЖНА быть осуществлена соответствующими механизмами безопасности.

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

13.8 Поведение кеша при ошибочных или незавершенных ответах

Кэш, который получает неполный ответ (например, с меньшим количеством байтов данных чем указанный в заголовке Content-Length) может хранить ответ. Однако, кэш ДОЛЖЕН обработать это как частичный ответ. Частичные ответы могут быть объединены как описано в разделе 13.5.4; результат мог бы быть полным ответом или мог бы все еще быть неравнодушным. Кэш не ДОЛЖЕН возвратить частичный ответ клиенту, явно не отмечая его также, используя 206 (Partial Content) код состояния. Кэш не ДОЛЖЕН возвратить частичный ответ, используя код состояния 200 (OK).

Если кэш получает 5xx ответ, пытаясь повторно проверить достоверность элемента, он может или отправить этот ответ клиенту запроса, или действовать, как будто сервер был не в состоянии отвечать. В последнем случае он МОЖЕТ возвратить ранее полученный ответ, если кэшируемый элемент не включает "must-revalidate" директива Cache-Control (см. раздел 14.9).

13.9 Побочные эффекты GET и HEAD

Если сервер происхождения явно не запрещает кэширование их ответов, у приложения методов GET И HEAD к любым ресурсам не ДОЛЖНО быть побочных эффектов, которые привели бы к ошибочному поведению, если эти ответы взяты от кэша. У них могут все еще быть побочные эффекты, но кэш не является обязаным рассматривать такие побочные эффекты в его кэширующих решениях. Кэши, как всегда ожидают, будут наблюдать явные ограничения сервера происхождения на кэширование.

Мы отмечаем одно исключение к этому правилу: так как некоторые приложения традиционно использовали GETs и HEADs с запросом URL (те, которые содержат "?" в rel_path части) чтобы выполнить операции с существенными побочными эффектами, кэши не ДОЛЖНЫ обработать ответы на такие URL как новые, если сервер не предоставляет явное время expiration. Это определенно означает, что ответы от HTTP/1.0 серверы для таких URI не должны быть взяты от кэша. См. раздел 9.1.1 для связанной с этим информации.

13.10 Ошибки после модификаций или стирания

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

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

В этом разделе фраза "лишает объект законной силы", означает, что кэш должен или удалить все экземпляры того объекта от его памяти, или должен отметить их как "недопустимые" и в потребности принудительного придания вновь юридической силы прежде, чем они смогут быть возвращены в ответ на последующий запрос.

Некоторые методы HTTP могут лишить объект законной силы. Это — или объект, упомянутый Request-URI, или Location или заголовками ответа Content-Location (если существующий). Эти методы:

Чтобы предотвратить атаки "отказ в обслуживании", недостоверность, основанная на URI в Location или заголовке Content-Location, ДОЛЖНА только быть выполнена, если ведущая часть — то же самое как в Request-URI.

13.11 Write-Through Mandatory

Все методы, которые, как могут ожидать, вызовут модификации к ресурсам сервера происхождения, ДОЛЖНЫ быть написаны через серверу происхождения. Это в настоящий момент включает все методы за исключением GET и HEAD. Кэш не ДОЛЖЕН ответить на такой запрос от клиента прежде передал запрос на прибывающий сервер, и получавший соответствующий ответ от прибывающего сервера. Это не препятствует тому, чтобы кэш отправил 100 (Continue) ответ прежде, чем прибывающий сервер ответил.

Альтернатива (известный как "write-back" или кэширующий "copy-back") не позволена в HTTP/1.1, из-за трудности предоставления непротиворечивого обновления и проблем, являющихся результатом сервера, кэша, или сетевого отказа до write-back.

13.12 Замена кэша

Если новый cachable (см. разделы 14.9.2, 13.2.5, 13.2.6 и 13.8) ответ получен от ресурса, в то время как любые существующие ответы для того же самого ресурса кэшируются, кэш ДОЛЖЕН использовать новый ответ, чтобы ответить на текущий запрос. Он может вставить его в память кэша и, если бы он отвечает всем другим требованиям, может использовать его, чтобы ответить на любые будущие запросы, которые ранее заставили бы старый ответ быть возвращенным. Если он вставляет новый ответ в память кэша, он должен следовать правилам в разделе 13.5.3.

Обратите внимание: Новый ответ, у которого есть старшее значение заголовка Date чем существующие кэшируемые ответы, не является cachable.

13.13 Списки history

У пользовательских агентов часто есть механизмы хронологии, например, кнопки "Back" и списки предыстории, которые могут использоваться, чтобы восстановить изображение объекта, найденного ранее в сеансе.

Механизмы хронологии и кэши отличны. В определенной хронологии механизмы не ДОЛЖНЫ попытаться показать семантически прозрачному представлению текущего состояния ресурса. Скорее механизм хронологии предназначается, чтобы показать точно, что видел пользователь в то время, когда ресурс был найден.

По умолчанию, время expiration не применяется к механизмам хронологии.

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

Это не должно быть рассмотрено, чтобы мешать механизму хронологии говорить пользователю, что представление может быть устарелым.

Обратите внимание: Если механизмы списка предыстории излишне будут препятствовать тому, чтобы пользователи рассмотрели устарелые ресурсы, то это будет иметь тенденцию вынуждать сервисных авторов избежать использовать HTTP управления expiration и управления кэша, когда они иначе хотели бы к. Сервисные авторы могут счесть его важным, что пользователи не быть представленными сообщения об ошибках или предупреждающие сообщения, когда они используют навигационные управления (например, BACK), чтобы рассмотреть ранее выбранные ресурсы. Даже при том, что иногда такие ресурсы не должен к кэшируемому, или должны истечь быстро, рассмотрения пользовательского интерфейса могут вынудить сервисных авторов прибегнуть к другим средствам предотвращения кэширующего (например "once-only" URL), чтобы не перенести эффекты ненадлежащим образом функционирующих механизмов хронологии.

14. Определения полей заголовка

Этот раздел определяет синтаксис и семантику всего стандартного HTTP/1.1 поля заголовка. Для полей заголовка объекта и отправитель и получатель ссылаются или на клиента или на сервер, в зависимости от того, кто отправляет и кто получает объект.

14.1 Accept

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

Accept         = "Accept" ":"
                 #( media-range [ accept-params ] )

media-range    = ( "*/*"
                 | ( type "/" "*" )
                 | ( type "/" subtype )
                 ) *( ";" parameter )

accept-params  = ";" "q" "=" qvalue *( accept-extension )

accept-extension = ";" token [ "=" ( token | quoted-string ) ]

Звездочка "*" символ используется к типам информации группы в диапазоны, с "*/*" индикация всех типов информации и "type / *" индикация всех подтипов того type. media-range МОЖЕТ включить мультимедийные параметры type, которые применимы к тому диапазону.

Каждый media-range МОЖЕТ сопровождаться одним или более accept-params, начиная с "q" parameter для того, чтобы указать относительный качественный коэффициент. Первый "q" parameter (если любой) отделяет media-range parameter от accept-params. Качественные коэффициенты позволяют пользователю или user agent указывать относительную степень предпочтения тому media-range, используя масштаб qvalue от 0 до 1 (раздел 3.9). Значение по умолчанию — q=1.

Обратите внимание: Использование "q" имени parameter, чтобы отделить мультимедийные параметры type от параметров расширения Accept происходит из-за исторической практики. Хотя это предотвращает любой мультимедийный type parameter, названный "q" от того, чтобы быть используемым с мультимедийным диапазоном, такому событию, как полагают, вряд ли дают нехватку любых "q" параметров в носителях IANA системный реестр type и редкое использование любых мультимедийных параметров type в Accept. Будущие типы информации должны быть отговорены регистрировать любой parameter, названный "q".

Пример

Accept: audio/*; q=0.2, audio/basic

ДОЛЖЕН быть интерпретирован как, "я предпочитаю audio/basic, но отправляю мне любой звуковой type, если он — лучшее доступное после 80%-ой скидки с цены по качеству." Если номер поля заголовка Accept присутствует, то предположено, что клиент принимает все типы информации. Если поле заголовка Accept присутствует, и если сервер не может отправить ответ, который является приемлемым согласно объединенному значению поля Accept, то сервер ДОЛЖЕН отправить 406 (not acceptable) ответ.

Более сложный пример

Accept: text/plain; q=0.5, text/html,
        text/x-dvi; q=0.8, text/x-c

Устно, это было бы интерпретировано как "text/html, и text/x-c — предпочтительные типы информации, но если они не существуют, затем отправьте text/x-dvi объект, и если это не существует, отправьте объект text/plain."

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

Accept: text/*, text/html, text/html;level=1, */*

имейте следующее старшинство:

  1. text/html; level=1
  2. text/html
  3. text/ *
  4. */*

Мультимедийный коэффициент качества type, связанный с данным type, определен, находя мультимедийный диапазон с самым высоким старшинством, которое соответствует тому type. Например,

Accept: text/*;q=0.3, text/html;q=0.7, text/html;level=1,
        text/html;level=2;q=0.4, */*;q=0.5

заставил бы следующие значения быть связанными:

text/html;level=1         = 1
text/html                 = 0.7
text/plain                = 0.3
image/jpeg                = 0.5
text/html;level=2         = 0.4
text/html;level=3         = 0.7

Обратите внимание: user agent можно предоставить с набором значения по умолчанию качественных значений для определенных мультимедийных диапазонов. Однако, если user agent не закрытая система, которая не может взаимодействовать с другими агентами предоставления, этот набор значения по умолчанию должен быть конфигурируемым пользователем.

14.2 Accept-Charset

Поле заголовка запроса Accept-Charset может использоваться, чтобы указать, какие наборы символов являются приемлемыми для ответа. Это поле позволяет клиентам, способным к пониманию более полных или наборов символов специального назначения сообщать о той возможности на сервер, который способен к представлению документов в тех наборах символов. Набор символов ISO8859-1 может быть предположен, чтобы быть приемлемым для всех пользовательских агентов.

Accept-Charset = "Accept-Charset" ":"
          1#( charset [ ";" "q" "=" qvalue ] )

Значения набора символов описаны в разделе 3.4. Каждому charset можно дать связанное качественное значение, которое представляет предпочтение пользователя этому charset. Значение по умолчанию — q=1. Пример

Accept-Charset: iso-8859-5, unicode-1-1;q=0.8

Если номер заголовка Accept-Charset присутствует, значение по умолчанию — то, что любой набор символов является приемлемым. Если заголовок Accept-Charset присутствует, и если сервер не может отправить ответ, который является приемлемым согласно заголовку Accept-Charset, то сервер ДОЛЖЕН отправить ошибочный ответ с 406 (not acceptable) код состояния, хотя отправка недопустимого ответа также позволена.

14.3 Accept-Encoding

Поле заголовка запроса Accept-Encoding похоже на Accept, но ограничивает значения content-coding (раздел 14.12), которые являются приемлемыми в ответе.

Accept-Encoding  = "Accept-Encoding" ":"
                          #( content-coding )

Пример его использования

Accept-Encoding: compress, gzip

Если номер заголовка Accept-Encoding присутствует в запросе, сервер МОЖЕТ предположить, что клиент примет любое кодирование контента. Если заголовок AcceptEncoding присутствует, и если сервер не может отправить ответ, который является приемлемым согласно заголовку Accept-Encoding, то сервер ДОЛЖЕН отправить ошибочный ответ с 406 (Not Acceptable) код состояния.

Пустое значение Accept-Encoding указывает, что ни один не является приемлемым.

14.4 Accept-Language

Поле заголовка запроса Accept-Language похоже на Accept, но ограничивает набор естественных языков, которые предпочтены как ответ на запрос.

Accept-Language = "Accept-Language" ":"
                  1#( language-range [ ";" "q" "=" qvalue ] )

language-range  = ( ( 1*8ALPHA *( "-" 1*8ALPHA ) ) | "*" )

Каждому language-range МОЖНО дать связанное качественное значение, которое представляет оценку предпочтения пользователя языкам, определенным тем диапазоном. Качественные значения по умолчанию значения к "q=1". Например,

Accept-Language: da, en-gb;q=0.8, en;q=0.7

означал бы: "я предпочитаю датский язык, но приму британский вариант английского языка и другие типы английского языка." language-range соответствует language-tag, если он точно равняется тэгу, или если он точно равняется префиксу тэга таким образом, что первый символ тэга после префикса "-".

Специальный диапазон "*", если представлено в поле Accept-Language, соответствует каждому тэгу, которому не соответствует любой другой диапазон, существующий в поле Accept-Language.

Обратите внимание: Это использование префикса, соответствующего правилу, не подразумевает, что языковые тэгы назначены языкам таким способом, которым он всегда истинен что, если пользователь поймет язык с определенным тэгом, то этот пользователь также поймет все языки с тэгами, для которых этот тэг — префикс. Префиксное правило просто позволяет использование префиксных тэгов если дело обстоит так.

Языковой коэффициент качества, назначенный language-tag полем Accept-Language, является качественным значением самого длинного languagerange в поле, которое соответствует language-tag. Если никакой languagerange в поле не соответствует тэгу, языковой назначенный коэффициент качества 0. Если номер заголовка Accept-Language присутствует в запросе, сервер ДОЛЖЕН предположить, что все языки являются одинаково приемлемыми. Если заголовок Accept-Language присутствует, то все языки, которые назначены качественный коэффициент, больше чем 0, являются приемлемыми.

Он может противоречить ожиданиям частной жизни пользователя отправить заголовок Accept-Language с полными лингвистическими персональными настройками пользователя в каждом запросе. Для обсуждения этого выпуска, см. раздел 15.7.

Обратите внимание: Поскольку ясность очень зависит от индивидуального пользователя, рекомендуется, чтобы клиентские приложения сделали вариант лингвистического предпочтения доступным пользователю. Если вариант не сделан доступным, то поле заголовка Accept-Language не должно быть дано в запросе.

14.5 Accept-Ranges

Поле заголовка ответа Accept-Ranges позволяет серверу указывать свое принятие запросов диапазона на ресурс:

Accept-Ranges     = "Accept-Ranges" ":" acceptable-ranges

acceptable-ranges = 1#range-unit | "none"

Серверы происхождения, которые принимают запросы диапазона байта, МОГУТ отправить

Accept-Ranges: bytes

но не будьте обязаными делать так. Клиенты МОГУТ генерировать запросы диапазона байта не получая этот заголовок для вовлеченного ресурса.

Серверы, которые не принимают вида запроса диапазона на ресурс, МОГУТ отправить

Accept-Ranges: none

советовать клиенту не делать попытку запроса диапазона.

14.6 Age

Поле заголовка ответа Age передает оценку отправителя количества времени, так как ответ (или его придание вновь юридической силы) был сгенерирован в сервере происхождения. Кэшируемый ответ "нов", если его возраст не превышает свое время существования свежести. значения Age вычислены как определено в разделе 13.2.3.

Age = "Age" ":" age-value

age-value = delta-seconds

Значения Age — неотрицательные десятичные целые числа, представляя время мгновенно. Если кэш получает значение, большее чем наибольшее положительное целое число, он может представить, или если любое его переполнение вычислений возраста, он ДОЛЖЕН передать заголовок Age со значением 2147483648 (2^31). HTTP/1.1 кэши ДОЛЖЕН отправить заголовок Age в каждом ответе. Кэши ДОЛЖНЫ использовать арифметический type по крайней мере 31 бита диапазона.

14.7 Allow

Поле заголовка объекта Allow перечисляет набор методов, поддерживаемых ресурсом, идентифицированным Request-URI. Цель этого поля состоит в том, чтобы строго информировать получателя правильных методов, связанных с ресурсом. Поле заголовка Allow ДОЛЖНО присутствовать в 405 (Method Not Allowed) ответ.

Allow          = "Allow" ":" 1#method

Пример использования:

Allow: GET, HEAD, PUT

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

Однако, индикации, данные значением SHOULD поля заголовка Allow сопровождаться. Фактический набор позволенных методов определен сервером происхождения во время каждого запроса.

Полю заголовка Allow МОЖНО предоставить с запросом PUT, чтобы рекомендовать методам поддерживаться новым или измененным ресурсом. Сервер не является обязаным поддерживать эти методы и ДОЛЖЕН включить заголовок Allow в ответ, дающий фактические поддерживаемые методы.

Прокси не ДОЛЖЕН изменить поле заголовка Allow, даже если он не понимает все указанные методы, так как у user agent МОГУТ быть другие средства сообщения с сервером происхождения.

Поле заголовка Allow не указывает, какие методы реализованы на уровне сервера. Серверы МОГУТ использовать поле заголовка ответа Public (раздел 14.35), чтобы описать, какие методы реализованы на сервере в целом.

14.8 Authorization

user agent, который желает аутентифицировать себя с сервером обычно, но не обязательно, после получения 401 ответа — МОЖЕТ сделать так, включая поле заголовка запроса Authorization в запрос. Значение поля Authorization состоит из credentials, содержащих опознавательную информацию user agent для области ресурса, который запрашивают.

Authorization  = "Authorization" ":" credentials

Идентификация доступа HTTP описана в разделе 11. Если запрос аутентифицируется, и область указана, те же самые credentials ДОЛЖНЫ быть правильными для всех других запросов в пределах этой области.

Когда общедоступный кэш (см. раздел 13.7) получает запрос, содержащий поле Authorization, он не ДОЛЖЕН возвратить соответствующий ответ как ответ на любой другой запрос, если одно из следующих специфичных исключений не держится:

  1. Если ответ включает "proxy-revalidate" директива Cache-Control, кэш МОЖЕТ использовать тот ответ в ответе на последующий запрос, но кэш прокси-сервера ДОЛЖЕН сначала повторно проверить достоверность его с сервером происхождения, используя заголовки запроса от нового запроса, чтобы позволить серверу происхождения аутентифицировать новый запрос.
  2. Если ответ включает "must-revalidate" директива Cache-Control, кэш МОЖЕТ использовать тот ответ в ответе на последующий запрос, но все кэши ДОЛЖНЫ сначала повторно проверить достоверность его с сервером происхождения, используя заголовки запроса от нового запроса, чтобы позволить серверу происхождения аутентифицировать новый запрос.
  3. Если ответ включает "public" директива Cache-Control, он может быть возвращен в ответ на любой последующий запрос.

14.9 Cache-Control

Общее поле заголовка Cache-Control используется, чтобы определить директивы, которым ДОЛЖНЫ повиноваться все кэширующие механизмы вдоль цепочки запроса/ответа. Директивы определяют, что поведение должно было предотвратить кэши от неблагоприятного сталкивания с запросом или ответом. Эти директивы обычно отменяют значение по умолчанию, кэширующее алгоритмы. Директивы кэша однонаправлены в этом, присутствие директивы в запросе не подразумевает, что та же самая директива должна быть дана в ответе.

Обратите внимание: Тот HTTP/1.0 кэши, возможно, не реализует Cache-Control и может только реализовать Pragma: no-cache (см. раздел 14.32).

Через директивы кэша нужно пройти прокси или межсетевым приложением, независимо от их значения для того приложения, так как директивы могут быть применимыми ко всем получателям вдоль цепочки запроса/ответа. Он не возможен определить cachedirective для специфичного кэша.

Cache-Control   = "Cache-Control" ":" 1#cache-directive

cache-directive = cache-request-directive
                | cache-response-directive
cache-request-directive =
                  "no-cache" [ "=" <"> 1#field-name <"> ]
                | "no-store"
                | "max-age" "=" delta-seconds
                | "max-stale" [ "=" delta-seconds ]
                | "min-fresh" "=" delta-seconds
                | "only-if-cached"
                | cache-extension

cache-response-directive =
                  "public"
                | "private" [ "=" <"> 1#field-name <"> ]
                | "no-cache" [ "=" <"> 1#field-name <"> ]
                | "no-store"
                | "no-transform"
                | "must-revalidate"
                | "proxy-revalidate"
                | "max-age" "=" delta-seconds
                | cache-extension

cache-extension = token [ "=" ( token | quoted-string ) ]

Когда директива появляется без любого 1#field-name parameter, директива применяется ко всему запросу или ответу. Когда такая директива появляется с 1#field-name parameter, она применяется только к именованному полю или полям, а не к остальной части запроса или ответа. Этот механизм поддерживает расширяемость; реализации будущих версий протокола HTTP могут применить эти директивы к полям заголовка, не определенным в HTTP/1.1.

Директивы управления кэша могут быть разделены на эти общие категории:

14.9.1 Что кэшируемо (Cachable)

По умолчанию, ответ — cachable, если требования метода запроса, полей заголовка запроса, и состояния ответа указывают, что он — cachable. Раздел 13.4 суммирует эти значения по умолчанию для cachability. Следующие директивы ответа Cache-Control позволяют серверу происхождения отменять значение по умолчанию cachability ответа:

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

Обратите внимание: Большинство HTTP/1.0 кэши не будет распознавать или повиноваться этой директиве.

14.9.2 Что может быть сохранено кэшем

Цель директивы no-store состоит в том, чтобы предотвратить небрежный выпуск или задержание секретной информации (например, на резервных магнитных лентах). Директива no-store применяется ко всему сообщению, и может быть отправлена или в ответе или в запросе. Если передано запрос, кэш не ДОЛЖЕН хранить часть или этого запроса или любого ответа на него. Если передано ответ, кэш не ДОЛЖЕН хранить часть или этого ответа или запроса, который выявлял его. Эта директива применяется и к non-shared и к разделенным кэшам. "Не ДОЛЖЕН хранить" в этих средствах контекста, что кэш не ДОЛЖЕН преднамеренно хранить информацию в неразрушающейся памяти, и ДОЛЖЕН заставить лучшее усилие попытаться удалить информацию из энергозависимой памяти настолько быстро насколько возможно после пересылки их.

Даже когда эта директива связана с ответом, пользователи могут явно хранить такой ответ за пределами кэширующей системы (например, с диалогом "Save As"). Буфера хронологии могут хранить такие ответы как часть их нормальной операции.

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

14.9.3 Модификации основного механизма устаревания

Время expiration объекта может быть указано сервером происхождения, используя заголовок Expires (см. раздел 14.21). Альтернативно, он может быть указан, используя директиву max-age в ответе.

Если ответ включает и заголовок Expires и директиву max-age, директива max-age отменяет заголовок Expires, даже если заголовок Expires является более ограничительным. Это правило позволяет серверу происхождения предоставлять, для данного ответа, более длинное время expiration к HTTP/1.1 (или позже) кэш чем к HTTP/1.0 кэш. Это может быть полезно, если определенный HTTP/1.0 кэши ненадлежащим образом вычисляет возрасты или времена expiration, возможно из-за десинхронизируемых часов.

Обратите внимание: Большинство старших кэшей, не совместимых с этой спецификацией, не реализует директив Cache-Control. Сервер происхождения, желающий использовать директиву Cache-Control, которая ограничивает, но не предотвращает, кэшируя HTTP/1.1-compliant, кэширует, может использовать требование, чтобы директива max-age отменила заголовок Expires, и факт, что non-HTTP/1.1-compliant кэши не наблюдают директиву max-age.

Другие директивы позволяют user agent изменять основной механизм expiration. Эти директивы могут быть указаны на запросе:

Если кэш возвращает устарелый ответ, или из-за директивы max-stale по запросу, или потому что кэш конфигурирован, чтобы отменить время expiration ответа, кэш ДОЛЖЕН прикрепить заголовок Warning к устарелому ответу, используя Warning 10 (Ответ является устарелым).

14.9.4 Перепроверки правильности кэша и средства управления перезагрузкой

Иногда user agent, возможно, хочет или должен настоять, чтобы кэш повторно проверил достоверность своего элемента кэша с сервером происхождения (и не только со следующим кэшем вдоль пути на сервер происхождения), или перезагружать его элемент кэша от сервера происхождения. придание вновь юридической силы End-to-end может быть необходимым, если или кэш или сервер происхождения оценили слишком высоко время expiration кэшируемого ответа. перезагрузка End-to-end может быть необходимой, если элемент кэша стал разрушенным по некоторым причинам.

Придание вновь юридической силы End-to-end можно запросить или когда у клиента нет его собственной локальной кэшируемой копии, когда мы называем его "неопределенным непрерывным приданием вновь юридической силы", или когда у клиента действительно есть локальная кэшируемая копия, когда мы называем его "специфичным непрерывным приданием вновь юридической силы."

Клиент может определить эти три вида действия, используя директивы запроса CacheControl:

Когда промежуточный кэш вызван, посредством max-age =0 директив, повторно проверить достоверность ее собственного элемента кэша, и клиент предоставил ее собственный объект для проверки правильности в запросе, предоставленный объект для проверки правильности может отличаться от объекта для проверки правильности, в настоящий момент сохраненного с элементом кэша. В этом случае, кэш может использовать любой объект для проверки правильности в создании его собственного запроса, не затрагивая семантическую прозрачность.

Однако, вариант объекта для проверки правильности может затронуть производительность. Лучший подход для промежуточного кэша, чтобы использовать его собственный объект для проверки правильности, делая его запрос. Если ответы сервера с 304 (Not Modified), то кэш должен возвратить свою теперь утвержденную копию клиенту с 200 (OK) ответ. Если ответы сервера с новым объектом и объектом для проверки правильности кэша, однако, промежуточный кэш должен сравнить возвращенный объект для проверки правильности с тем, предоставленным в запросе клиента, используя сильную функцию сравнения. Если объект для проверки правильности клиента равен серверу происхождения, то промежуточный кэш просто возвращается 304 (Not Modified). Иначе, он возвращает новый объект с 200 (OK) ответ.

Если запрос включает директиву no-cache, он не должен включить min-fresh, max-stale, или max-age.

В некоторых случаях, например, времена чрезвычайно плохого сетевого обеспечения связи, клиент, возможно, хочет кэш, чтобы возвратить только те ответы, которые оно в настоящий момент хранило, а не перезагрузить или повторно проверить достоверность с сервером происхождения. Чтобы сделать это, клиент может включить директиву only-if-cached в запрос. Если он получает эту директиву, кэш ДОЛЖЕН или ответить, используя кэшируемый элемент, который совместим с другими ограничениями запроса, или отвечать 504 (Gateway Timeout) состояние. Однако, если группой кэшей управляют как объединенная система с хорошим внутренним обеспечением связи, такой запрос МОЖЕТ быть отправлен в пределах той группы кэшей.

Поскольку кэш может быть конфигурирован, чтобы проигнорировать указанное время expiration сервера, и потому что клиентский запрос может включить директиву max-stale (который имеет подобный эффект), протокол также включает механизм для сервера происхождения, чтобы потребовать придания вновь юридической силы элемента кэша на любом последующем использовании. Когда директива must-revalidate присутствует в ответе, полученном кэшем, тот кэш не ДОЛЖЕН использовать элемент после того, как он становится устарелым, чтобы ответить на последующий запрос без первой перепроверки достоверности его с сервером происхождения. (То есть, кэш должен сделать непрерывное придание вновь юридической силы каждый раз, если, базируемый исключительно на значении Expires ИЛИ max-age сервера происхождения, кэшируемый ответ является устарелым).

Директива must-revalidate необходима, чтобы поддержать надежную операцию для определенных возможностей протокола. При всех обстоятельствах HTTP/1.1 кэш ДОЛЖЕН повиноваться директиве must-revalidate; в частности если кэш не может достигнуть сервера происхождения по какой-нибудь причине, он ДОЛЖЕН генерировать 504 (Gateway Timeout) ответ.

Серверы должны отправить директиву must-revalidate, если и только если отказ повторно проверить достоверность запроса на объекте мог закончиться неправильной операцией, например, тихо невыполняемой финансовой транзакцией. Получатели не ДОЛЖНЫ предпринять автоматизированное действие, которое нарушает эту директиву, и не ДОЛЖНО автоматически предоставить неутвержденную копию объекта, если придание вновь юридической силы терпит неудачу.

Хотя этому не рекомендуют, пользовательские агенты, действующие при серьезных ограничениях обеспечения связи, могут нарушить эту директиву, но, если так, ДОЛЖНЫ явно предупредить пользователя, что неутвержденный ответ был предоставлен. Предупреждение ДОЛЖНО быть предоставлено на каждом неутвержденном доступе, и ДОЛЖНО потребовать явного пользовательского подтверждения.

У директивы proxy-revalidate есть то же самое значение как mustrevalidate директива, за исключением того, что он не применяется к non-shared кэши user agent. Он может использоваться на ответе на аутентифицированный запрос, чтобы разрешить кэшу пользователя хранить и более позднее возвращение ответ, не будучи должный повторно проверить достоверность его (так как он уже аутентифицировался однажды тем пользователем), все еще требуя прокси, которые обслуживают много пользователей, чтобы повторно проверить достоверность каждый раз когда (чтобы удостовериться, что каждый пользователь аутентифицировался). Обратите внимание, что такие аутентифицированные ответы также нуждаются в кэше public управлять директивой, чтобы позволить им кэшироваться вообще.

14.9.5 Директива No-Transform

Разработчики промежуточных кэшей (прокси) нашли полезным конвертировать мультимедийный type определенных тел объекта. Прокси мог бы, например, конвертировать между форматами изображений, чтобы оставить свободное место кэша или уменьшить количество трафика на медленной ссылке. HTTP до настоящего времени был тих на этих трансформациях. Серьезные операционные проблемы уже произошли, однако, когда эти трансформации применили к телам объекта, предназначенным для определенных видов приложений. Например, приложения для медицинского отображающего, научного анализа данных и тех, используя непрерывную идентификацию, все зависят от получения тела объекта, которое является битом для бита, идентичного оригинальному телу объекта.

Поэтому, если ответ включает директиву no-transform, промежуточный кэш или прокси не ДОЛЖНЫ изменить те заголовки, которые перечислены в разделе 13.5.2 как являющийся подчиненным директиве no-transform. Это подразумевает, что кэш или прокси не должны изменить аспект тела объекта, которое указано этими заголовками.

14.9.6 Расширения средств управления кэшем

Поле заголовка Cache-Control может распространяться с помощью одной или более лексем cache-extension, каждого с опциональным назначенным значением.

Информационные расширения (те, которые не требуют изменения в поведении кэша) могут быть добавлены, не изменяя семантику других директив. Поведенческие расширения проектированы, чтобы работать, действуя как модификаторы к существующей основе директив кэша. И новая директива и стандартная директива предоставлены, таким образом что приложения, которые не понимают новую директиву, будут значение по умолчанию к поведению, определенному в соответствии со стандартной директивой, и теми, которые понимают, что новая директива распознает его как изменение требований, связанных со стандартной директивой. Таким образом, расширения к директивам Cache-Control могут быть сделаны, не требуя изменений основного протокола.

Этот механизм расширения зависит от кэша HTTP, повинуясь всем директивам управления кэша, определенным для его родного HTTP — версия, повинуясь определенным расширениям, и игнорируя все директивы, чтобы он не понял.

Например, рассмотрите гипотетическую новую директиву ответа под названием "community", который действует как модификатор к директиве "private". Мы определяем эту новую директиву, чтобы означать, что в дополнение к любому кэшу non-shared любой кэш, который разделен только членами community, названного в пределах его значения, может кэшировать ответ. Сервер происхождения, желающий позволить community "UCI" использовать иначе ответ private в их общедоступном кэше (ах), может сделать так, включая

Cache-Control: private, community="UCI"

Кэш, видя это поле заголовка будет действовать правильно, даже если кэш не поймет "community" cache-extension, так как он будет также видеть и понимать директиву "private" и таким образом значение по умолчанию к безопасному поведению. ДОЛЖНЫ быть проигнорированы нераспознанные директивы кэша; предположено, что любой cache-directive вероятно, чтобы быть нераспознанным HTTP/1.1 кэш будет объединен со стандартными директивами (или значение по умолчанию ответа cachability) таким образом, что поведение кэша останется минимально правильным, даже если кэш не поймет расширение (я).

14.10 Connection

Общее поле заголовка Connection позволяет отправителю определять опции, которые заданы для того определенного подключения и не ДОЛЖНЫ быть сообщены прокси по дальнейшим подключениям.

У заголовка Connection есть следующая грамматика:

Connection-header = "Connection" ":" 1#(connection-token)
connection-token  = token

HTTP/1.1 прокси ДОЛЖЕН разобрать поле заголовка Connection прежде, чем сообщение будет отправлено и, для каждого connection-token в этом поле, удалите любое поле (я) заголовка из сообщения с тем же самым именем как connection-token. об опциях Connection сообщает присутствие connection-token в поле заголовка Connection, не любым соответствующим дополнительным полем (ями) заголовка, так как дополнительное поле заголовка нельзя отправить, если нет никаких параметров, связанных с той опцией подключения. HTTP/1.1 определяет "близкую" опцию подключения для отправителя, чтобы сообщить об этом, подключение будет закрыто после завершения ответа. Например,

Connection: close

или в запросе или в полях заголовка ответа указывает, что подключение не должно рассматриваться 'постоянный' (раздел 8.1) после того, как текущий запрос/ответ завершен.

HTTP/1.1 приложения, которые не поддерживают постоянные подключения, ДОЛЖЕН включить "близкую" опцию подключения в каждое сообщение.

14.11 Content-Base

Поле заголовка объекта Content-Base может использоваться, чтобы определить основной URI для того, чтобы разрешить относительные URL в пределах объекта. Это поле заголовка описано как Основа в RFC 1808, который, как ожидают, будет пересмотрен.

Content-Base      = "Content-Base" ":" absoluteURI

Если номер поля Content-Base присутствует, основной URI объекта определен любой его Content-Location (если, что Content-Location URI является абсолютный URI), или URI, используемый, чтобы инициализировать запрос, в том порядке очередности. Обратите, однако, внимание, что основной URI содержания в пределах тела объекта может быть переопределен в пределах того тела объекта.

14.12 Content-Encoding

Поле заголовка объекта Content-Encoding используется как модификатор к media-type. Когда представлено, его значение указывает, какое дополнительное кодирование контента применили к телу объекта, и таким образом какое декодирование механизмов ДОЛЖНО быть применено, чтобы получить media-type, на который ссылается поле заголовка Content-Type. Content-Encoding прежде всего используется, чтобы позволить документу быть сжатым, не теряя identity его базового мультимедийного type.

Content-Encoding  = "Content-Encoding" ":" 1#content-coding

Кодирование контента определено в разделе 3.5. Пример его использования

Content-Encoding: gzip

Content-Encoding — характеристика объекта, идентифицированного Request-URI. Как правило, тело объекта сохранено с этим кодированием и только декодировано прежде, чем отдать или аналогичное использование.

Если множественные кодирования применили к объекту, кодирование контента ДОЛЖНО быть перечислено в порядке, в котором они были применены.

Дополнительная информация о параметрах MAY кодирования быть предоставленными другими полями заголовка объекта, не определенными этой спецификацией.

14.13 Content-Language

Поле заголовка объекта Content-Language описывает естественный язык (и) намеченной аудитории для включенного объекта. Обратите внимание, что это, возможно, не эквивалентно всем языкам, используемым в пределах тела объекта.

Content-Language  = "Content-Language" ":" 1#language-tag

Языковые тэгы определены в разделе 3.10. Первичная цель Content-Language состоит в том, чтобы позволить пользователю идентифицировать и дифференцировать объекты согласно собственному предпочтительному языку пользователя. Таким образом, если контент тела предназначен только для датско-грамотной аудитории, соответствующее поле

Content-Language: da

Если номер Content-Language указан, значение по умолчанию — то, что контент предназначен для всех языковых зрителей. Это может означать, что отправитель не полагает, что он специфичен для любого естественного языка, или что отправитель не знает, для которого языка он предназначен.

Множественные языки МОГУТ быть перечислены для контента, который предназначен для множественных зрителей. Например, преобразованная копия "Соглашения относительно Waitangi," представленный одновременно в оригинальном Маори и английских версиях, запросила бы

Content-Language: mi, en

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

Пример был бы языковым учебником для начинающих новичка, например, "Первым Уроком на латыни,", который ясно предназначен, чтобы использоваться англо-грамотной аудиторией. В этом случае, Content-Language должен только включить "в".

Content-Language можно применить к любому мультимедийному type — он не ограничен текстовыми документами.

14.14 Content-Length

Поле заголовка объекта Content-Length указывает размер тела сообщения, в десятичном числе октетов, отправленных получателю или, в случае метода HEAD, у размера тела объекта, которое отправили бы, был запрос, GET.

Content-Length    = "Content-Length" ":" 1*DIGIT

Пример

Content-Length: 3495

Приложения ДОЛЖНЫ использовать это поле, чтобы указать размер тела сообщения, которое будет передано, независимо от мультимедийного type объекта. Он должен быть возможен для получателя надежно определить конец HTTP/1.1 запросы, содержащие тело объекта, например, потому что у запроса есть правильное поле Content-Length, Transfer-Encoding использований: chunked или многослойное тело.

Любой Content-Length, больше чем или равный, чтобы обнулить, является правильным значением.

Раздел 4.4 описывает, как определить длину тела сообщения, если Content-Length не дан.

Обратите внимание: Значение этого поля значительно отличается от соответствующего определения MIME, где он — опциональное поле, используемое в пределах контента-type "message/external-body". В HTTP его НУЖНО отправить всякий раз, когда длина сообщения может быть определена до того, чтобы быть переданным.

14.15 Content-Location

Поле заголовка объекта Content-Location может использоваться, чтобы предоставить местоположение ресурса для объекта, включенного в сообщение. В случае, где ресурсу связали множественные объекты с ним, и теми объектами фактически, имеют отдельные местоположения, которыми к ним можно было бы индивидуально обратиться, сервер должен предоставить Content-Location для определенного варианта, который возвращен. Кроме того, сервер ДОЛЖЕН предоставить Content-Location для ресурса, соответствующего объекту ответа.

Content-Location = "Content-Location" ":"
                  ( absoluteURI | relativeURI )

Если номер поля заголовка Content-Base присутствует, значение ContentLocation также определяет базовый унифицированный указатель информационного ресурса для объекта (см. раздел 14.11).

Значение Content-Location не замена для оригинала, который запрашивают URI; он — только оператор местоположения ресурса, соответствующего этому определенному объекту во время запроса.

Будущие запросы МОГУТ использовать Content-Location URI, если желание состоит в том, чтобы идентифицировать источник того определенного объекта.

Кэш не может предположить, что объект с Content-Location, отличным от URI, используемого, чтобы отыскать его, может использоваться, чтобы ответить на более поздние запросы на том Content-Location URI. Однако, ContentLocation может использоваться, чтобы дифференцироваться между множественными объектами, найденными от отдельного запрошенного ресурса, как описано в разделе 13.6.

Если Content-Location — относительный URI, URI интерпретируется относительно любого Content-Base URI, предоставленный в ответе. Если номер Content-Base предоставлен, относительный URI интерпретируется относительно Request-URI.

14.16 Content-MD5

Полем заголовка объекта Content-MD5, как определено в RFC 1864 [23], является digest MD5 тела объекта с целью предоставления непрерывной проверки целостности сообщения (МИКРОСХЕМА MIC) тела объекта.

Примечание: МИКРОСХЕМА MIC хороша для того, чтобы обнаружить случайную модификацию тела объекта в пути, но не является доказательством против опасных атак.

Content-MD5   = "Content-MD5" ":" md5-digest

md5-digest    = <base64 of 128 bit MD5 digest as per RFC 1864>

Поле заголовка Content-MD5 может быть сгенерировано сервером происхождения, чтобы функционировать как проверка целостности тела объекта. Только серверы происхождения могут генерировать поле заголовка Content-MD5; прокси и шлюзы не ДОЛЖНЫ генерировать его, поскольку это победило бы его значение как непрерывную проверку целостности. Любой получатель тела объекта, включая шлюзы и прокси, МОЖЕТ проверить что значение digest в этих соответствиях поля заголовка то из тела объекта как получено.

digest MD5 вычислен основанный на контенте тела объекта, включая любой Content-Encoding, который был применен, но не включение любого Transfer-Encoding, который, возможно, применили к телу сообщения. Если сообщение получено с Transfer-Encoding, то кодирование должно быть удалено до проверки значения Content-MD5 против полученного объекта.

У этого есть результат, что digest вычислен на октетах тела объекта точно как, и в порядке, который, их отправили бы, если бы номер Transfer-Encoding применялся.

HTTP распространяет RFC 1864, чтобы разрешить digest быть вычисленным для типов информации составного объекта MIME (например, multipart/* и message/rfc822), но это не изменяется, как digest вычислен как определено в предыдущем абзаце.

Обратите внимание: Есть несколько последствий этого. Тело объекта для составных типов может содержать многих body-parts, каждый с его собственным MIME и заголовками HTTP (включение Content-MD5, Content-Transfer-Encoding, и заголовков Content-Encoding). Если у части тела есть ContentTransfer-кодирование или заголовок Content-Encoding, предположено, что контенту части тела применили кодирование, и часть тела включена в Content-MD5, который digest как — то есть, после приложения. Поле заголовка Transfer-Encoding не позволено в пределах body-parts.

Обратите внимание: В то время как определение Content-MD5 — точно то же самое для HTTP как в RFC 1864 для тел объекта MIME, есть несколько способов, по которым приложение Content-MD5 к телам объекта HTTP отличается от его приложения до тел объекта MIME. Каждый — тот HTTP, в отличие от MIME, не использует Content-Transfer-Encoding, и действительно использует Transfer-Encoding и Content-Encoding. Другой — тот HTTP, более часто использует двоичные типы контента чем MIME, таким образом он стоит отмечать, что в таких случаях порядок байта, используемый, чтобы вычислить digest, является порядком байта передачи, определенным для type. Наконец, HTTP позволяет передачу типов текстов с любым из нескольких соглашений конца строки и не только канонической формы, используя CRLF.

Обратите внимание: Преобразование всех концов строки к CRLF нельзя сделать прежде, чем вычислить или проверить digest: соглашение конца строки, используемое в тексте, фактически переданном, нужно оставить неизменным, вычисляя digest.

14.17 Content-Range

Заголовок объекта Content-Range отправляют с частичным телом объекта, чтобы определить, где в полном теле объекта частичное тело должно быть вставлено. Он также указывает полный размер полного тела объекта. Когда сервер возвращает частичный ответ клиенту, он должен описать и степень диапазона, охваченного ответом, и длину всего тела объекта.

Content-Range = "Content-Range" ":" content-range-spec

content-range-spec      = byte-content-range-spec

byte-content-range-spec = bytes-unit SP first-byte-pos "-"
                          last-byte-pos "/" entity-length

entity-length           = 1*DIGIT

В отличие от значений байта-ranges-specifier, byte-content-range-spec может только определить один диапазон, и должен содержать абсолютные позиции байта для обоих первый и последний байт диапазона.

byte-content-range-spec, значение last-byte-pos которого — меньше чем его значение first-byte-pos, или чье значение entity-length меньше чем или равно своему значению last-byte-pos, недопустим. Получатель недопустимого byte-content-range-spec ДОЛЖЕН проигнорировать его и любой контент, переданный наряду с ним.

Примеры значений byte-content-range-spec, предполагая, что объект содержит в общей сложности 1234 байта:

* The first 500 bytes:
     bytes 0-499/1234

* The second 500 bytes:
     bytes 500-999/1234

* All except for the first 500 bytes:
     bytes 500-1233/1234

* The last 500 bytes:
     bytes 734-1233/1234

Когда сообщение HTTP включает контент одного диапазона (например, ответ на запрос на один диапазон, или к запросу на ряд диапазонов, которые накладываются без любых отверстий), этот контент передан с заголовком Content-Range, и заголовком Content-Length, показывающим числу байтов, фактически переданных. Например,

HTTP/1.1 206 Partial content
Date: Wed, 15 Nov 1995 06:25:24 GMT
Last-modified: Wed, 15 Nov 1995 04:58:08 GMT
Content-Range: bytes 21010-47021/47022
Content-Length: 26012
Content-Type: image/gif

Когда сообщение HTTP включает контент множественных диапазонов (например, ответ на запрос на множественные ненакладывающиеся диапазоны), они переданы как многослойное сообщение MIME. Многослойный контент-type MIME, используемый с этой целью, определен в этой спецификации, чтобы быть "multipart/byteranges". См. приложение 19.2 для его определения.

Клиент, который не может декодировать MIME multipart/byteranges сообщение, не должен попросить множественные диапазоны байта в отдельном запросе.

Когда клиент запрашивает множественные диапазоны байта в одном запросе, сервер ДОЛЖЕН возвратить их в порядке, что они появлялись в запросе.

Если сервер игнорирует спецификации диапазона-байта, потому что он недопустим, сервер должен обработать запрос, как будто недопустимое поле заголовка Range не существовало. (Обычно, это означает возвращение 200 ответов, содержащих полный объект). Причина состоит в том, что единственное время, клиент сделает такой недопустимый запрос, — то, когда объект меньше чем объект, найденный предшествующим запросом.

14.18 Content-Type

Поле заголовка объекта Content-Type указывает мультимедийный type тела объекта, отправленного получателю или, в случае метода HEAD у мультимедийного type, который отправили бы, был запрос, GET.

Content-Type   = "Content-Type" ":" media-type

Типы информации определены в разделе 3.7. Пример поля

Content-Type: text/html; charset=ISO-8859-4

Дальнейшее обсуждение методов для того, чтобы идентифицировать мультимедийный type объекта предоставлено в разделе 7.2.1.

14.19 Date

Общее поле заголовка Date представляет дату и время, в которую сообщение было порождено, имея ту же самую семантику как orig-дата в RFC 822. Полевое значение — HTTP-date, как описано в разделе 3.3.1.

Date  = "Date" ":" HTTP-date

Пример

Date: Tue, 15 Nov 1994 08:12:31 GMT

Если сообщение получено через прямое подключение с user agent (в случае запросов) или сервер происхождения (в случае ответов), то дата может быть предположена, чтобы быть текущей датой в конце получения. Однако, так как дата — поскольку ему верит происхождение — важна для оценки кэшируемых ответов, серверы происхождения ДОЛЖНЫ включить поле заголовка Date во все ответы. Клиенты ДОЛЖНЫ только отправить поле заголовка Date в сообщениях, которые включают entitybody, поскольку в случае PUT и POST запрашивает, и даже тогда он является опциональным. Полученное сообщение, у которого нет поля заголовка Date, ДОЛЖНО быть назначено один получателем, если сообщение будет кэшироваться тем получателем или gatewayed через протокол, который требует Date.

В теории дата ДОЛЖНА представить момент непосредственно перед тем, как объект сгенерирован. Практически, дата может быть сгенерирована в любое время во время происхождения сообщения, не затрагивая его семантическое значение.

Формат Date — абсолютная дата и время как определено HTTP-date в разделе 3.3; он ДОЛЖЕН быть передан RFC1123 [8] — формат даты.

14.20 ETag

Поле заголовка объекта ETag определяет тэг объекта для связанного объекта. Заголовки, используемые с тэгами объекта, описаны в разделах 14.20, 14.25, 14.26 и 14.43. Тэг объекта может использоваться для сравнения с другими объектами от того же самого ресурса (см. раздел 13.3.2).

ETag = "ETag" ":" entity-tag

Примеры:

ETag: "xyzzy"
ETag: W/"xyzzy"
ETag: ""

14.21 Expires

Поле заголовка объекта Expires дает дату/время, после которой ответ должен рассматриваться устарелый. Устарелый элемент кэша не может обычно возвращаться кэшем (или кэш прокси-сервера или кэш user agent), если он сначала не утвержден с сервером происхождения (или с промежуточным кэшем, у которого есть новая копия объекта). См. раздел 13.2 для дальнейшего обсуждения модели expiration.

Присутствие поля Expires не подразумевает, что оригинальный ресурс изменится или прекратит существовать в, прежде, или после того времени.

Формат — абсолютная дата и время как определено HTTP-date в разделе 3.3; он ДОЛЖЕН быть в формате RFC1123-date:

Expires = "Expires" ":" HTTP-date

Пример его использования

Expires: Thu, 01 Dec 1994 16:00:00 GMT

Обратите внимание: Если ответ включает поле Cache-Control в директиву max-age, та директива отменяет поле Expires.

HTTP/1.1 клиенты и кэши ДОЛЖЕН обработать другие недопустимые форматы даты, особенно включая значение "0", как в прошлом (то есть, "уже истек").

Отмечать ответ как "уже истекается," сервер происхождения должен использовать дату Expires, которая равна значению заголовка Date. (См. правила для вычислений expiration в разделе 13.2.4).

Чтобы не отметить ответ как "никогда, окончания функционирования," сервер происхождения должен использовать дату Expires приблизительно один год со времени ответ, отправляют. HTTP/1.1 серверы не должен отправить датам Expires больше чем один год в будущем.

Присутствие поля заголовка Expires со значением даты некоторого времени в будущем на ответе, который иначе по умолчанию был бы некэшируемым, указывает, что ответ — cachable, если не обозначено иначе полем заголовка Cache-Control (раздел 14.9).

14.22 From

Поле заголовка запроса From, если дано, ДОЛЖНО содержать интернет-адрес электронной почты для человеческого пользователя, который управляет запросом user agent. Адрес ДОЛЖЕН быть пригодным для использования машиной, столь же определенный почтовым ящиком в RFC 822 (как обновлено RFC 1123):

From   = "From" ":" mailbox

Пример:

From: webmaster@w3.org

Это поле заголовка МОЖЕТ использоваться для того, чтобы регистрировать цели и как средство для того, чтобы идентифицировать источник недопустимых или нежелательных запросов. Он не ДОЛЖЕН использоваться как небезопасная форма защиты доступа. Интерпретация этого поля — то, что запрос выполняется от имени данного человека, кто принимает ответственность за выполненный метод. В частности агенты робота ДОЛЖНЫ включить этот заголовок так, чтобы с человеком, ответственным за выполнение робота, можно было войти в контакт, если проблемы происходят на конце получения.

Интернет-адрес электронной почты в этом поле MAY быть отдельным от интернет-хоста, который выпустил запрос. Например, когда запрос передают через прокси, адрес оригинальной запрашивающей стороны ДОЛЖЕН использоваться.

Обратите внимание: Клиент не ДОЛЖЕН отправить поле заголовка From без одобрения пользователя, поскольку он может находиться в противоречии с интересами частной жизни пользователя или политикой безопасности их сайта. Строго рекомендуется, чтобы пользователь был в состоянии отключить, допустить, и изменить значение этого поля в любое время до запроса.

14.23 Host

Поле заголовка запроса Host определяет интернет-хост и число port ресурса, который запрашивают, как получено из оригинала URL, данный пользователем или относящий ресурс (обычно HTTP URL, как описано в разделе 3.2.2). Значение MUST поля Host представляет сетевое местоположение сервера происхождения или шлюза, данного оригиналом URL. Это позволяет серверу происхождения или шлюзу дифференцироваться между внутренне неоднозначными URL, например, root "/" URL сервера для множественных имен хоста на отдельном адресе IP.

Host = "Host" ":" host [ ":" port ]    ; Section 3.2.2

"Хост" без любого перемещения информация port подразумевает значение по умолчанию port для обслуживания, которое запрашивают (например, "80" для HTTP URL). Например, запрос на сервере происхождения для http://www.w3.org/pub/WWW/ДОЛЖЕН включить:

GET /pub/WWW/ HTTP/1.1
Host: www.w3.org

Клиент ДОЛЖЕН включить поле заголовка Host в весь HTTP/1.1 сообщения запроса в Интернете (то есть, в любом сообщении, соответствующем запросу на URL, который включает интернет-ведущий адрес для обслуживания, которое запрашивают). Если поле Host уже не присутствует, HTTP/1.1 прокси ДОЛЖЕН добавить поле Host к сообщению запроса до пересылки его в Интернете. Весь HTTP на базе Internet/1.1 серверы ДОЛЖЕН ответить 400 кодами состояния к любому HTTP/1.1 сообщение запроса, которое испытывает недостаток в поле заголовка Host.

См. разделы 5.2 и 19.5.1 для других требований, касающихся Host.

14.24 If-Modified-Since

Поле заголовка запроса If-Modified-Since используется с методом GET, чтобы сделать его условным выражением: если запрошенный вариант не был изменен со времени, указанного в этом поле, объект не будет возвращен из сервера; вместо этого, 304 (не измененный) ответ будут возвращены без любого тела сообщения.

If-Modified-Since = "If-Modified-Since" ":" HTTP-date

Пример поля:

If-Modified-Since: Sat, 29 Oct 1994 19:43:31 GMT

Метод GET с заголовком If-Modified-Since и номером запросов заголовка Range, что идентифицированный объект быть переданным, только если он был изменен начиная с даты, данной заголовком If-Modified-Since.

Алгоритм для того, чтобы определить это включает следующие случаи:

Цель этой возможности состоит в том, чтобы позволить эффективное обновление кэшируемой информации с минимальным количеством операционных издержек.

Обратите внимание: То, что поле заголовка запроса Range изменяет значение If-Modified-Since; см. раздел 14.36 за полные детали.

Те времена If-Modified-Since интерпретируются сервером, часы которого не могут быть синхронизированы с клиентом.

Обратите внимание, что если клиент использует произвольную дату в заголовке If-Modified-Since вместо даты, взятой от заголовка Last-Modified для того же самого запроса, клиент должен знать о факте, что эта дата интерпретируется в понимании сервера времени. Клиент должен рассмотреть несинхронизированные часы и округление проблем из-за других кодирований времени между клиентом и сервером. Это включает возможность условий состязания, если документ изменился между временем, его сначала запросили и Если-ModifiedSince дата последующего запроса, и возможность clockskew-связанных проблем, если дата If-Modified-Since получена из часов клиента без исправления на часы сервера.

Исправления для других основ времени между клиентом и сервером в лучшем случае приблизительны из-за сетевой задержки.

14.25 If-Match

Поле заголовка запроса If-Match используется с методом, чтобы сделать его условным выражением. Клиент, у которого есть один или более объектов, ранее полученных из ресурса, может проверить, что один из тех объектов является текущим, включая список их связанных тэгов объекта в поле заголовка If-Match. Цель этой возможности состоит в том, чтобы позволить эффективное обновление кэшируемой информации с минимальным количеством операционных издержек. Он также используется, при модифицировании запросов, предотвратить небрежную модификацию неправильной версии ресурса.

Как особый случай, значение "*" соответствует любому текущему объекту ресурса.

If-Match = "If-Match" ":" ( "*" | 1#entity-tag )

Если бы любой из тэгов объекта соответствует тэгу объекта объекта, который был бы возвращен в ответ на подобный запрос GET (без заголовка If-Match) на том ресурсе, или если "*" дан, и любой текущий объект существует для того ресурса, то сервер МОЖЕТ выполнить запрошенный метод, как будто поле заголовка If-Match не существовало.

Сервер ДОЛЖЕН использовать сильную функцию сравнения (см. раздел 3.11), чтобы сравнить тэгы объекта в If-Match.

Если ни один из объекта не отмечает соответствие, или если "*" дан, и никакой текущий объект не существует, сервер не ДОЛЖЕН выполнить запрошенный метод, и ДОЛЖЕН возвратить 412 (Precondition Failed) ответ. Это поведение является самым полезным, когда клиент хочет предотвратить метод модифицирования, например, PUT, от изменения ресурса, который изменился, так как последний клиент отыскал его.

Если бы запрос, без поля заголовка If-Match, закончился бы чем-нибудь кроме 2xx состояние, то заголовок If-Match ДОЛЖЕН быть проигнорирован.

Значение "If-Match: *" то, что метод SHOULD выполнен, если представление, выбранное сервером происхождения (или кэшем, возможно, используя механизм Vary, см. раздел 14.43), существует, и не ДОЛЖНО быть выполнено, если представление не существует.

Запрос должен был обновить ресурс (например, PUT) МОЖЕТ включить поле заголовка If-Match, чтобы сообщить об этом метод MUST запроса НЕ быть примененным, если объект, соответствующий значению If-Match (отдельный тэг объекта), больше не является представлением того ресурса. Это позволяет пользователю указывать, что они не желают, чтобы запрос был успешен, если ресурс был изменен без их знания.

Примеры:

If-Match: "xyzzy"
If-Match: "xyzzy", "r2d2xxxx", "c3piozzzz"
If-Match: *

14.26 If-None-Match

Поле заголовка запроса If-None-Match используется с методом, чтобы сделать его условным выражением. Клиент, у которого есть один или более объектов, ранее полученных из ресурса, может проверить, что ни один из тех объектов не является текущим, включая список их связанных тэгов объекта в поле заголовка If-None-Match. Цель этой возможности состоит в том, чтобы позволить эффективное обновление кэшируемой информации с минимальным количеством операционных издержек. Он также используется, при модифицировании запросов, предотвратить небрежную модификацию ресурса, который, как было известно, не существовал.

Как особый случай, значение "*" соответствует любому текущему объекту ресурса.

If-None-Match = "If-None-Match" ":" ( "*" | 1#entity-tag )

Если бы любой из тэгов объекта соответствует тэгу объекта объекта, который был бы возвращен в ответ на подобный запрос GET (без заголовка If-None-Match) на том ресурсе, или если "*" дан, и любой текущий объект существует для того ресурса, то сервер не ДОЛЖЕН выполнить запрошенный метод. Вместо этого если бы методом запроса был GET или HEAD, то сервер ДОЛЖЕН ответить 304 (Not Modified) ответ, включая связанные с кэшем поля заголовка объекта (особенно ETag) одного из объектов, которые соответствовали. Для всех других методов запроса сервер ДОЛЖЕН ответить состоянием 412 (Precondition Failed).

См. раздел 13.3.3 для правил о том, как определить, отмечают ли два объекта соответствие. Слабая функция сравнения может только использоваться с запросами HEAD или GET.

Если ни один из объекта не отмечает соответствие, или если "*" дан, и никакой текущий объект не существует, то сервер МОЖЕТ выполнить запрошенный метод, как будто поле заголовка If-None-Match не существовало.

Если бы запрос, без поля заголовка If-None-Match, закончился бы чем-нибудь кроме 2xx состояние, то заголовок If-None-Match ДОЛЖЕН быть проигнорирован.

Значение "If-None-Match: *" то, что метод MUST НЕ выполнен, если представление, выбранное сервером происхождения (или кэшем, возможно, используя механизм Vary, см. раздел 14.43), существует, и ДОЛЖНО быть выполнено, если представление не существует.

Эта возможность может быть полезной в предотвращении гонок между операциями PUT.

Примеры:

If-None-Match: "xyzzy"
If-None-Match: W/"xyzzy"
If-None-Match: "xyzzy", "r2d2xxxx", "c3piozzzz"
If-None-Match: W/"xyzzy", W/"r2d2xxxx", W/"c3piozzzz"
If-None-Match: *

14.27 If-Range

Если клиент имеет частичную копию объекта в его кэше, и желает иметь современную копию всего объекта в его кэше, он мог использовать заголовок запроса Range с условным GET (или, используя или, используя оба из If-Unmodified-Since и If-Match). Однако, если условие терпит неудачу, потому что объект был изменен, клиент должен будет тогда сделать второй запрос, чтобы получить все текущее тело объекта.

Заголовок If-Range позволяет клиенту "короткому замыканию" второй запрос. Неофициально, его значение, «если объект неизменен, отправьте мне часть (и), которую я пропускаю; иначе, отправьте мне весь новый объект».

If-Range = "If-Range" ":" ( entity-tag | HTTP-date )

Если клиент не имеет никакого тэга объекта для объекта, но действительно имеет дату LastModified, он может использовать ту дату в заголовке If-Range. (Сервер может различить правильный HTTP-date и любую форму entity-tag, исследуя не больше, чем два символа). заголовок If-Range должен только использоваться вместе с заголовком Range, и должен быть проигнорирован, если запрос не включает заголовок Range, или если сервер не поддерживает операцию поддиапазона.

Если тэг объекта, данный в заголовке If-Range, соответствует текущему тэгу объекта для объекта, то сервер должен предоставить указанный поддиапазон объекта, используя 206 (Partial content) ответ. Если тэг объекта не соответствует, то сервер должен возвратить весь объект, используя 200 (OK) ответ.

14.28 If-Unmodified-Since

Поле заголовка запроса If-Unmodified-Since используется с методом, чтобы сделать его условным выражением. Если запрошенный ресурс не был изменен со времени, указанного в этом поле, сервер должен выполнить запрошенную операцию, как будто заголовок If-Unmodified-Since не присутствовал.

Если запрошенный вариант был изменен с указанного времени сервер не ДОЛЖЕН выполнить запрошенную операцию, и ДОЛЖЕН возвратить 412 (Precondition Failed).

If-Unmodified-Since = "If-Unmodified-Since" ":" HTTP-date

Пример поля:

If-Unmodified-Since: Sat, 29 Oct 1994 19:43:31 GMT

Если бы запрос обычно (то есть, без заголовка If-Unmodified-Since) закончился бы чем-нибудь кроме 2xx состояние, IfUnmodified-с-тех-пор, заголовок должен быть проигнорирован.

Если указанная дата недопустима, заголовок проигнорирован.

14.29 Last-Modified

Поле заголовка объекта Last-Modified указывает дату и время, в которую сервер происхождения полагает, что вариант был последний измененный.

Last-Modified  = "Last-Modified" ":" HTTP-date

Пример его использования

Last-Modified: Tue, 15 Nov 1994 12:45:26 GMT

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

Сервер происхождения не ДОЛЖЕН отправить дату Last-Modified, которая позже чем время сервера происхождения сообщения. В таких случаях, где последняя модификация ресурса указала бы некоторое время в будущем, сервер ДОЛЖЕН заменить ту дату датой происхождения сообщения.

Сервер происхождения должен получить значение Last-Modified объекта как близко насколько возможно ко времени, когда он генерирует значение Date его ответа. Это позволяет получателю делать точную оценку времени модификации объекта, особенно если объект изменяется около времени, когда ответ сгенерирован.

HTTP/1.1 серверы ДОЛЖЕН отправить Last-Modified всякий раз, когда выполнимо.

14.30 Location

Поле заголовка ответа Location используется, чтобы переадресовать получателя в местоположение кроме Request-URI для завершения запроса или идентификации нового ресурса. Для 201 (Created) ответы, Location — Location нового ресурса, который был создан запросом. Для 3xx ответы, местоположение ДОЛЖНО указать предпочтительный URL сервера для автоматического перенаправления к ресурсу. Полевое значение состоит из отдельного абсолютного URL.

Location       = "Location" ":" absoluteURI

Пример

Location: http://www.w3.org/pub/WWW/People.html

Обратите внимание: Поле заголовка Content-Location (раздел 14.15) отличается от Location, в котором Content-Location идентифицирует оригинальное местоположение объекта, включенного в запрос. Он поэтому возможен для ответа содержать поля заголовка и для Location и для Content-Location. Также см. раздел 13.10 для требований кэша некоторых методов.

14.31 Max-Forwards

Поле заголовка запроса Max-Forwards может использоваться с методом TRACE (раздел 14.31), чтобы ограничить число прокси или шлюзов, которые могут отправить запрос следующему прибывающему серверу. Это может быть полезно, когда клиент пытается проследить цепочку запроса, которая оказывается неудачей или выполнением цикла в середине цепочки.

Max-Forwards   = "Max-Forwards" ":" 1*DIGIT

Значение Max-Forwards — десятичное целое число, указывающее остающееся число раз, которое может быть отправлено это сообщение запроса.

Каждый прокси или межсетевой получатель запроса TRACE, содержащего поле заголовка MaxForwards, ДОЛЖНЫ проверить и обновить его значение до пересылки запроса. Если полученное значение — нуль (0), получатель не ДОЛЖЕН отправить запрос; вместо этого, он ДОЛЖЕН ответить как конечный получатель 200 (OK) ответ, содержащий полученное сообщение запроса как тело объекта ответа (как описано в разделе 9.8). Если полученное значение Max-Forwards больше чем нуль, то отправленное сообщение ДОЛЖНО содержать обновленное поле MaxForwards со значением, уменьшенным одним (1).

Поле заголовка Max-Forwards ДОЛЖНО быть проигнорировано для всех других методов, определенных этой спецификацией и для любых методов расширения, для которых он явно не упоминается как часть того определения метода.

14.32 Pragma

Общее поле заголовка Pragma используется, чтобы включить implementationspecific директивы, которые могут применяться к любому получателю вдоль цепочки запроса/ответа. Все директивы псевдокомментария определяют опциональное поведение с точки зрения протокола; однако, некоторые системы МОГУТ потребовать, чтобы поведение было совместимо с директивами.

Pragma            = "Pragma" ":" 1#pragma-directive

pragma-directive  = "no-cache" | extension-pragma
extension-pragma  = token [ "=" ( token | quoted-string ) ]

Когда директива no-cache присутствует в сообщении запроса, приложение SHOULD отправляют запрос к серверу происхождения, даже если у него есть кэшируемая копия того, что запрашивают. У этой директивы псевдокомментария есть та же самая семантика как no-cache cache-directive (см. раздел 14.9), и определен здесь для назад совместимости с HTTP/1.0. Клиенты ДОЛЖНЫ включить оба поля заголовка, когда запрос no-cache отправляют серверу, не известному, чтобы быть HTTP/1.1 совместимый.

Через директивы Pragma НУЖНО пройти прокси или межсетевым приложением, независимо от их значения для того приложения, так как директивы могут быть применимыми ко всем получателям вдоль цепочки запроса/ответа. Он не возможен определить псевдокомментарий для специфичного получателя; однако, любая директива псевдокомментария, не релевантная получателю, ДОЛЖНА быть проигнорирована тем получателем.

HTTP/1.1 клиенты не ДОЛЖЕН отправить заголовок запроса Pragma. HTTP/1.1 кэши ДОЛЖЕН обработать "Pragma: no-cache", как будто клиент отправил "Cache-Control: no-cache". Никакие новые директивы Pragma не будут определены в HTTP.

14.33 Proxy-Authenticate

Поле заголовка ответа Proxy-Authenticate ДОЛЖНО быть включено как часть 407 (Proxy Authentication Required) ответ. Полевое значение состоит из требования, которое указывает схему аутентификации и параметры, применимые к прокси для этого Request-URI.

Proxy-Authenticate  = "Proxy-Authenticate" ":" challenge

Процесс идентификации доступа HTTP описан в разделе 11.

В отличие от WWW-Authenticate, поле заголовка Proxy-Authenticate применяется только на текущее подключение и не ДОЛЖНО быть передано нижестоящим клиентам. Однако, промежуточный прокси, возможно, должны получить его собственные credentials, запрашивая их от нижестоящего клиента, который при некоторых обстоятельствах появится, как будто прокси отправляет поле заголовка Proxy-Authenticate.

14.34 Proxy-Authorization

Поле заголовка запроса Proxy-Authorization позволяет клиенту идентифицировать себя (или его пользователь) к прокси, который требует идентификации. Значение поля Proxy-Authorization состоит из credentials, содержащих опознавательную информацию user agent для прокси и/или области ресурса, который запрашивают.

Proxy-Authorization     = "Proxy-Authorization" ":" credentials

Процесс идентификации доступа HTTP описан в разделе 11.

В отличие от Authorization, поле заголовка Proxy-Authorization применяется только к следующему экспортному прокси, который требовал идентификацию, используя поле Proxy-Authenticate. Когда множественные прокси используются в цепочке, поле заголовка Proxy-Authorization использовано первым экспортным прокси, который ожидал получать credentials. Прокси МОЖЕТ передать credentials от клиентского запроса до следующего прокси, если это — механизм, которым прокси совместно аутентифицируют данный запрос.

14.35 Public

Поле заголовка ответа Public перечисляет набор методов, поддерживаемых сервером. Цель этого поля состоит в том, чтобы строго информировать получателя возможностей сервера относительно необычных методов. Перечисленные методы могут или, возможно, не применимы к Request-URI; поле заголовка Allow (раздел 14.7) МОЖЕТ использоваться, чтобы указать, что методы учитывали определенный URI.

Public         = "Public" ":" 1#method

Пример использования:

Public: OPTIONS, MGET, MHEAD, GET, HEAD

Это поле заголовка применяется только на сервер, непосредственно подключенный клиенту (то есть, самый близкий сосед в цепочке подключений). Если ответ проходит через прокси, прокси ДОЛЖЕН или удалить поле заголовка Public или заменить его одним применимым к его собственным возможностям.

14.36 Range

14.36.1 Byte Ranges

Так как все объекты HTTP представлены в сообщениях HTTP как последовательности байтов, понятие диапазона байта значимо для любого объекта HTTP. (Однако, не все клиенты и серверы должен поддержать byterange операции).

Спецификации диапазона байта в HTTP применяются к последовательности байтов в теле объекта (не обязательно то же самое как тело сообщения).

Операция диапазона байта может определить один диапазон байтов, или ряд диапазонов в пределах отдельного объекта.

ranges-specifier = byte-ranges-specifier

byte-ranges-specifier = bytes-unit "=" byte-range-set

byte-range-set  = 1#( byte-range-spec | suffix-byte-range-spec )

byte-range-spec = first-byte-pos "-" [last-byte-pos]

first-byte-pos  = 1*DIGIT

last-byte-pos   = 1*DIGIT

Значение first-byte-pos в спецификациях диапазона-байта дает байтовое смещение первого байта в диапазоне. Значение last-byte-pos дает байтовое смещение последнего байта в диапазоне; то есть, указанные позиции байта являются содержащими. Байтовые смещения начинаются в нуле.

Если значение last-byte-pos присутствует, он должен быть больше чем или равным first-byte-pos в тех спецификациях диапазона-байта, или byterange-спецификации недопустимы. Получатель недопустимых спецификаций диапазона-байта должен проигнорировать его.

Если значение last-byte-pos отсутствует, или если значение больше чем или равно текущей длине тела объекта, last-byte-pos взят, чтобы быть равным меньше текущая длина entitybody в байтах.

Его вариантом last-byte-pos клиент может ограничить число байтов, найденных, не зная размер объекта.

suffix-byte-range-spec = "-" suffix-length

suffix-length = 1*DIGIT

suffix-byte-range-spec используется, чтобы определить суффикс тела объекта, длины, данной значением suffix-length. (Таким образом, эта форма определяет последние байты N тела объекта). Если объект более короток чем указанный suffix-length, все тело объекта используется.

Примеры значений байта-ranges-specifier (предполагающий тело объекта длины 10000):

* The first 500 bytes (byte offsets 0-499, inclusive):
       bytes=0-499

* The second 500 bytes (byte offsets 500-999, inclusive):
       bytes=500-999

* The final 500 bytes (byte offsets 9500-9999, inclusive):
       bytes=-500
    Or
       bytes=9500-

* The first and last bytes only (bytes 0 and 9999):
       bytes=0-0,-1

* Several legal but not canonical specifications of the second 500 bytes (byte offsets 500-999, inclusive):
       bytes=500-600,601-999
       bytes=500-700,601-999

14.36.2 Запросы Поиска Range

Запросы поиска HTTP, используя условные или безоговорочные методы GET могут запросить один или более поддиапазонов объекта, вместо всего объекта, используя заголовок запроса Range, который применяется к объекту, возвращенному как результат запроса:

Range = "Range" ":" ranges-specifier

Сервер МОЖЕТ проигнорировать заголовок Range. Однако, HTTP/1.1 серверы происхождения и промежуточные кэши ДОЛЖЕН поддержать диапазоны байта когда возможно, так как Range поддерживает эффективное восстановление от частично неудавшихся передач, и поддерживает эффективный частичный поиск больших объектов.

Если сервер поддерживает заголовок Range и указанный диапазон, или диапазоны соответствуют объекту:

В некоторых случаях, он может быть более соответствующим использовать заголовок If-Range (см. раздел 14.27) в дополнение к заголовку Range.

Если прокси, который поддерживает диапазоны, получает запрос Range, перешлите запрос на прибывающий сервер, и получает весь объект в ответ, он ДОЛЖЕН только возвратить запрошенный диапазон его клиенту. Он ДОЛЖЕН хранить весь полученный ответ в его кэше, если это совместимо с его политикой выделения кэша.

14.37 Referer

Referer [так] поле заголовка запроса позволяет клиенту определять, для преимущества сервера, адрес (URI) ресурса, из которого был получен Request-URI ("referrer", хотя поле заголовка написано c орфографическими ошибками). заголовок запроса Referer позволяет, что сервер, чтобы генерировать списки обратных ссылок к ресурсам для интереса, регистрации, оптимизировал кэширование, и т.д. Он также позволяет устаревшим или напечатанным с ошибкой ссылкам быть прослеженными для обслуживания. Поле Referer НЕЛЬЗЯ отправить, если бы Request-URI был получен из источника, у которого нет его собственного URI, например, ввода от пользовательской клавиатуры.

Referer        = "Referer" ":" ( absoluteURI | relativeURI )

Пример:

Referer: http://www.w3.org/hypertext/DataSources/Overview.html

Если полевое значение — частичный URI, оно ДОЛЖНО быть интерпретировано относительно Request-URI. URI не ДОЛЖЕН включить фрагмент.

Обратите внимание: Поскольку источник ссылки может быть информацией private или может показать иначе источник информации private, строго рекомендуется, чтобы пользователь был в состоянии выбрать, отправляют ли поле Referer. Например, у браузерного клиента могло быть переключение переключателя для того, чтобы просмотреть открыто/анонимно, который соответственно допустит/отключит отправке информации From и Referer.

14.38 Retry-After

Поле заголовка ответа Retry-After может использоваться с 503 (Service Unavailable) ответ, чтобы указать, как долго обслуживание, как ожидают, будет недоступно клиенту запроса. Значение этого поля может быть или HTTP-date или целочисленным числом секунд (в десятичном числе) после времени ответа.

Retry-After  = "Retry-After" ":" ( HTTP-date | delta-seconds )

Два примера его использования

Retry-After: Fri, 31 Dec 1999 23:59:59 GMT
Retry-After: 120

В последнем примере задержка составляет 2 минуты.

14.39 Server

Поле заголовка ответа Server содержит информацию о программном обеспечении, используемом сервером происхождения, чтобы обработать запрос. Поле может содержать множественные лексемы продукта (раздел 3.8) и комментарии, идентифицирующие сервер и любые существенные промежуточные результаты. Лексемы продукта перечислены в порядке их значения для того, чтобы идентифицировать приложение.

Server         = "Server" ":" 1*( product | comment )

Пример:

Server: CERN/3.0 libwww/2.17

Если ответ отправляется через прокси, приложение MUST прокси НЕ изменяют заголовок ответа Server. Вместо этого он ДОЛЖЕН включить поле Via (как описано в разделе 14.44).

Обратите внимание: Раскрытие специфичной программной версии сервера может позволить серверу становиться более уязвимым для атак против программного обеспечения, которое, как известно, содержит бреши в защите. разработчики Server поощрены сделать это поле конфигурируемой опцией.

14.40 Transfer-Encoding

Общее поле заголовка Transfer-Encoding указывает то, что (если любой) type трансформации применили к телу сообщения, чтобы безопасно передать его между отправителем и получателем. Это отличается от Content-Encoding в этом, кодирование передачи — свойство сообщения, не объекта.

Transfer-Encoding       = "Transfer-Encoding" ":" 1#transfer-coding

Кодирование передачи определено в разделе 3.6. Пример:

Transfer-Encoding: chunked

Многие старший HTTP/1.0 приложения не понимают заголовок TransferEncoding.

14.41 Upgrade

Общий заголовок Upgrade позволяет клиенту определять, какие дополнительные протоколы взаимодействия он поддерживает и хотел бы использовать, если сервер находит, что он приспосабливает к протоколам переключения. Сервер ДОЛЖЕН использовать поле заголовка Upgrade в пределах 101 (Switching Protocols) ответ, чтобы указать, какой протокол (ы) переключаются.

Upgrade        = "Upgrade" ":" 1#product

Например,

Upgrade: HTTP/2.0, SHTTP/1.3, IRC/6.9, RTA/x11

Поле заголовка Upgrade предназначено, чтобы предоставить простой механизм для перехода от HTTP/1.1 к некоторому другому, несовместимому протоколу. Он делает так, разрешая клиенту рекламировать его желание использовать другой протокол, например, более позднюю версию HTTP с более высоким старшим номером версии, даже при том, что текущий запрос был сделан, используя HTTP/1.1.

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

Поле заголовка Upgrade только применяется к переключающимся протоколам прикладной программы на существующее подключение транспортного уровня. Upgrade не может использоваться, чтобы настоять на изменении протокола; его принятие и использование сервером являются опциональными. Возможности и характер взаимодействия прикладного уровня после изменения протокола полностью зависят от нового выбранного протокола, хотя первое действие после изменения протокола ДОЛЖНО быть ответом на начальный запрос HTTP, содержащий поле заголовка Upgrade.

Поле заголовка Upgrade только применяется к непосредственному подключению.

Поэтому, ключевое слово обновления ДОЛЖНО быть предоставлено в пределах поля заголовка Connection (раздел 14.10) всякий раз, когда Upgrade присутствует в HTTP/1.1 сообщение.

Поле заголовка Upgrade не может использоваться, чтобы указать переключение для протокола на другом подключении. С этой целью, он является более соответствующим использовать 301, 302, 303, или 305 ответов перенаправления.

Эта спецификация только определяет имя протокола "HTTP" для использования семьей Языков передачи гипертекста, как определено правилами управления версиями HTTP раздела 3.1 и будущего обновления этой спецификации. Любой token может использоваться как имя протокола; однако, он только будет полезен, если и клиент и сервер свяжут имя с тем же самым протоколом.

14.42 User-Agent

Поле заголовка запроса User-Agent содержит информацию о user agent, порождающем запрос. Это в статистических целях, трассировке нарушений протокола, и автоматизированном распознавании пользовательских агентов ради приспосабливания ответов, чтобы избежать определенных ограничений user agent. Пользовательские агенты ДОЛЖНЫ включить это поле в запросы. Поле может содержать множественные лексемы продукта (раздел 3.8) и комментарии, идентифицирующие агента и любые промежуточные результаты, которые являются существенной частью user agent. Условно, лексемы продукта перечислены в порядке их значения для того, чтобы идентифицировать приложение.

User-Agent     = "User-Agent" ":" 1*( product | comment )

Пример:

User-Agent: CERN-LineMode/2.15 libwww/2.17b3

14.43 Vary

Поле заголовка ответа Vary используется сервером, чтобы сообщить об этом, объект ответа был выбран из доступных представлений ответа, используя управляемые сервером переговоры (раздел 12). Fieldnames, перечисленные в заголовках Vary, являются таковыми из заголовков запроса. Значение поля Vary указывает или что данный набор полей заголовка охватывает размерности, по которым представление могло бы измениться, или что размерности дисперсии неопределены ("*") и таким образом могут измениться по любому аспекту будущих запросов.

Vary  = "Vary" ":" ( "*" | 1#field-name )

HTTP/1.1 сервер ДОЛЖЕН включить соответствующее поле заголовка Vary в любой cachable ответ, который подчинен управляемым сервером переговорам.

Выполнение так позволяет кэшу должным образом интерпретировать будущие запросы на том ресурсе и сообщает user agent о присутствии переговоров относительно того ресурса. Сервер ДОЛЖЕН включить соответствующее поле заголовка Vary в non-cachable ответ, который подчинен управляемым сервером переговорам, так как это могло бы предоставить user agent полезную информацию о размерностях, по которым мог бы измениться ответ.

Набор полей заголовка, названных значением поля Vary, известен как заголовки запроса "выбора".

Когда кэш получает последующий запрос, Request-URI которого определяет один или более входов кэша, включающих заголовок Vary, кэш не ДОЛЖЕН использовать такой элемент кэша, чтобы создать ответ на новый запрос, если все заголовки, названные в кэшируемом заголовке Vary, не присутствуют в новом запросе, и все сохраненные заголовки запроса выбора от предыдущего запроса соответствуют соответствующим заголовкам в новом запросе.

Заголовки запроса выбора от двух запросов определены, чтобы соответствовать, если и только если заголовки запроса выбора в первом запросе могут быть преобразованы к заголовкам запроса выбора во втором запросе, добавляя или удаляя линейный пробел (LWS) в местах, где этому позволяют соответствующая НОРМАЛЬНАЯ ФОРМА БЕКУСА-НАУРА, и/или объединение множественных messageheader полей с тем же самым именем поля, следующим правилам о заголовках сообщения в разделе 4.2.

Значение поля Vary "*" сигналы, что неопределенные параметры, возможно кроме содержания полей заголовка запроса (например, сетевой адрес клиента), играют роль в выборе представления ответа. Последующие запросы на том ресурсе могут только быть должным образом интерпретированы сервером происхождения, и таким образом кэш ДОЛЖЕН отправить (возможно условное выражение) запрос, даже когда ему кэшировали новый ответ для ресурса. См. раздел 13.6 для использования заголовка Vary кэшами.

Значение поля Vary, состоящее из списка сигналов имен полей, что представление, выбранное для ответа, основано на алгоритме выбора, который считает ТОЛЬКО перечисленные значения поля заголовка запроса в выборе самым соответствующим представлением. Кэш МОЖЕТ предположить, что тот же самый выбор будет сделан для будущих запросов с одинаковыми значениями для перечисленных имен полей, на протяжении времени, в которое ответ нов.

Данные имена полей не ограничены набором стандартных полей заголовка запроса, определенных этой спецификацией. Имена полей являются независящими от регистра.

14.44 Via

Общее поле заголовка Via ДОЛЖНО использоваться шлюзами и прокси, чтобы указать промежуточные протоколы и получателей между user agent и сервером на запросах, и между сервером происхождения и клиентом на ответах. Он походит на поле "Received" RFC 822 и предназначен, чтобы использоваться для того, чтобы проследить сообщение, пересылают, избегая циклов запроса, и идентифицируя возможности протокола всех отправителей вдоль цепочки запроса/ответа.

Via =  "Via" ":" 1#( received-protocol received-by [ comment ] )

received-protocol = [ protocol-name "/" ] protocol-version
protocol-name     = token
protocol-version  = token
received-by       = ( host [ ":" port ] ) | pseudonym
pseudonym         = token

received-protocol указывает версию протокола сообщения, полученного сервером или клиентом вдоль каждого сегмента цепочки запроса/ответа. Версия received-protocol добавлена к значению поля Via, когда сообщение отправлено так, чтобы информация о возможностях протокола приложений восходящего потока данных осталась видимой всем получателям.

protocol-name является опциональным, если и только если он был бы "HTTP". Поле received-by обычно — ведущее и опциональное число port сервера получателя или клиента, который впоследствии отправлял сообщение. Однако, если реальный хост рассматривается, чтобы быть секретной информацией, он МОЖЕТ быть заменен псевдонимом. Если port не дан, он МОЖЕТ быть предположен, чтобы быть значением по умолчанию port received-protocol.

Множественные значения поля Via представляют каждый прокси или шлюз, который отправил сообщение. Каждый получатель ДОЛЖЕН добавить его информацию таким образом, что исход упорядочен согласно последовательности пересылки приложений.

Комментарии МОГУТ использоваться в поле заголовка Via, чтобы идентифицировать программное обеспечение прокси получателя или шлюза, аналогичного полям заголовка Server и User-Agent. Однако, все комментарии в поле Via являются опциональными и МОГУТ быть удалены любым получателем до пересылки сообщения.

Например, сообщение запроса можно было отправить от HTTP/1.0 user agent к внутреннему прокси "Фреда" под кодовым названием, который использует HTTP/1.1, чтобы отправить запрос прокси public в nowhere.com, который завершает запрос, отправляя его серверу происхождения в www.ics.uci.edu.

У запроса, полученного www.ics.uci.edu, тогда было бы следующее поле заголовка Via:

Via: 1.0 fred, 1.1 nowhere.com (Apache/1.1)

Прокси и шлюзы, используемые как портал через сетевую межсетевую защиту, не ДОЛЖНЫ, по умолчанию, отправить имена и порты хостов в пределах области межсетевой защиты. Эта информация ДОЛЖНА только быть распространена если явно допущено. Если не допущенный, хост received-by какого-нибудь хоста позади межсетевой защиты ДОЛЖЕН быть заменен соответствующим псевдонимом для того хоста.

Для организаций, у которых есть сильные требования частной жизни сокрытия внутренних структур, прокси МОЖЕТ объединить упорядоченную подпоследовательность входов поля заголовка Via с идентичными значениями received-protocol в отдельное такой элемент. Например,

Via: 1.0 ricky, 1.1 ethel, 1.1 fred, 1.0 lucy

 мог быть сокращен к

Via: 1.0 ricky, 1.1 mertz, 1.0 lucy

Приложения не ДОЛЖНЫ объединить множественные входы, если они не все под тем же самым организационным управлением, и хосты были уже заменены псевдонимами. Приложения не ДОЛЖНЫ объединить входы, у которых есть другие значения received-protocol.

14.45 Warning

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

Заголовки Warning отправляют с ответами, используя:

Warning    = "Warning" ":" 1#warning-value

warning-value = warn-code SP warn-agent SP warn-text
warn-code  = 2DIGIT
warn-agent = ( host [ ":" port ] ) | pseudonym
                ; the name or pseudonym of the server adding
                ; the Warning header, for use in debugging
warn-text  = quoted-string

Ответ может нести больше чем один заголовок Warning.

Предупреждать — текст должен быть на естественном языке и наборе символов, который, наиболее вероятно, будет понятен человеческому пользователю, получающему ответ. Это решение может быть основано на любом доступном знании, например, местоположении кэша или пользователя, поля Accept-Language в запросе, поля Content-Language в ответе, и т.д. Язык значения по умолчанию является английским, и набор символов значения по умолчанию — ISO8859-1.

Если набор символов кроме ISO-8859-1 используется, он ДОЛЖЕН быть закодирован в том, чтобы предупреждать — текст, используя метод, описанный в RFC 1522 [14].

Любой сервер или кэш могут добавить заголовки Warning к ответу. Новые заголовки Warning должны быть добавлены после любых существующих заголовков Warning. Кэш не ДОЛЖЕН удалить заголовок Warning, который он получил с ответом. Однако, если кэш успешно проверяет достоверность элемента кэша, он ДОЛЖЕН удалить любые заголовки Warning, ранее приложенные к тому элементу кроме как определено для специфичных кодов Warning. Он ДОЛЖЕН тогда добавить любые заголовки Warning, полученные в ответе проверки достоверности. Другими словами, заголовки Warning — те, которые были бы присоединены к новому релевантному ответу.

Когда множественные заголовки Warning присоединены к ответу, user agent ДОЛЖЕН отобразить так многих из них насколько возможно, в порядке, что они появляются в ответе. Если он не возможен отобразить все предупреждения, user agent должен следовать за этой эвристикой:

Системы, которые генерируют множественные заголовки Warning, должны заказать им с этим поведением user agent в уме.

Это — список определенных в настоящий момент предупре-кодов, каждый с рекомендуемым предупреждает — текст на английском языке, и описание его значения.

14.46 WWW-Authenticate

Поле заголовка ответа WWW-Authenticate ДОЛЖНО быть включено в 401 (Unauthorized) ответные сообщения. Полевое значение состоит по крайней мере из одного требования, которое указывает схему (ы) аутентификации и параметры, применимые к Request-URI.

WWW-Authenticate  = "WWW-Authenticate" ":" 1#challenge

Процесс идентификации доступа HTTP описан в разделе 11. Пользовательские агенты ДОЛЖНЫ взять специальную заботу в парсинге значения поля WWW-Authenticate, если он содержит больше чем одно требование, или если больше чем одно поле заголовка WWW-Authenticate предоставлено, так как содержание требования может самостоятельно содержать отделенный запятыми список опознавательных параметров.

15. Положения о защите

Этот раздел предназначается, чтобы сообщить разработчикам приложений, информационным провайдерам, и пользователям ограничений безопасности в HTTP/1.1 как описано в соответствии с этим документом. Обсуждение не включает категорические решения показанных проблем, хотя оно действительно делает некоторые предложения для того, чтобы уменьшить угрозы безопасности.

15.1 Идентификация Клиентов

Схема аутентификации Basic не безопасный метод аутентификации пользователей, и при этом он в любом случае не защищает объект, который передан открытым текстом через физическую сеть, используемую как носитель. HTTP не препятствует тому, чтобы дополнительные схемы аутентификации и механизмы кодирования использовались, чтобы увеличить безопасность или суммирование расширений (например, схемы, чтобы использовать одноразовые пароли) к аутентификации Basic.

Самый серьезный недостаток в аутентификации Basic — то, что она заканчивается по существу передача открытого текста пароля пользователя по физической сети. Именно эта проблема Digest Authentication пытается обратиться.

Поскольку аутентификация Basic вовлекает передачу открытого текста паролей, он никогда не ДОЛЖЕН использоваться (без расширений), чтобы защитить чувствительную или ценную информацию.

Обычное использование аутентификации Basic в идентифицирующих целях — требование, чтобы пользователь предоставил имя пользователя и пароль как средство идентификации, например, в целях собрать точную статистику использования по серверу. Когда используется таким образом заманчиво думать, что нет никакой опасности в ее использовании, если незаконный доступ к защищенным документам не главное беспокойство. Это только правильно, если сервер выпускает и имя пользователя и пароль пользователям и в особенности не позволяет пользователю выбирать его или её собственный пароль.

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

Если сервер разрешает пользователям выбирать свои собственные пароли, то угроза не только незаконный доступ к документам относительно сервера но также и незаконный доступ к учетным записям всех пользователей, которые хотели использовать их пароль учетной записи. Если пользователям разрешают выбрать их собственный пароль, который также означает, что сервер должен поддержать файлы, содержащие (по-видимому зашифрованный) пароли. Многие из них могут быть паролями учетной записи пользователей возможно на отдаленных сайтах. Владелец или администратор такой системы могли очевидно взять на себя обязательства, если эта информация не сохранена безопасным видом.

Basic Authentication также уязвим для имитации поддельными серверами. Если пользователя можно привести, полагают, что он подключается к хосту, содержащему информацию, защищенную стандартной аутентификацией, когда фактически он подключается к враждебному серверу или шлюзу тогда, атакующий может запросить пароль, хранить его для более позднего использования, и симулировать ошибку. Этот type атаки не возможен с Digest Authentication [32]. разработчики Server ДОЛЖНЫ принять меры против возможности этого вида подделывания сценариями интерфейса компьютерной графики или шлюзами. В особенности очень опасно для сервера просто перевернуть подключение к шлюзу, так как тот шлюз может тогда использовать постоянный механизм подключения, чтобы участвовать во множественных транзакциях клиентом, олицетворяя оригинального сервера способом, который не является обнаруживаемым клиентом.

15.2 Предложение выбрать схему установления подлинност

HTTP/1.1 сервер может возвратиться, множественные требования с 401 (Аутентифицируют) ответ, и каждое требование может использовать другую схему. Порядок требований, возвращенных к user agent, находится в порядке, что сервер предпочел бы их быть выбранным. Сервер должен заказать свои требования с "самой безопасной" схемой аутентификации сначала. user agent должен хотеть как требование быть сделанным пользователю первым, который понимает user agent.

Когда сервер предлагает варианты схем аутентификации, используя заголовок WWW-Authenticate, "безопасность" идентификации только, поскольку опасный пользователь мог фиксировать набор требований и попытаться аутентифицировать себя, используя самые слабые из схем аутентификации. Таким образом, упорядочение служит больше, чтобы защитить credentials пользователя чем информация сервера.

Возможный "человек в середине" (MITM), атака должна была бы добавить слабую схему аутентификации к набору вариантов, надеясь, что клиент будет использовать тот, который предоставляет credentials пользователя (например пароль). Поэтому клиент должен всегда использовать самую сильную схему, которую он понимает от принятых вариантов.

Еще лучшая атака MITM должна была бы удалить все предлагаемые варианты, и вставлять требование, которое запрашивает аутентификацию Basic. Поэтому пользовательские агенты, которые обеспокоены этим видом атаки, могли помнить самую сильную схему аутентификации, которую когда-либо запрашивает сервер, и создать предупреждающее сообщение, которое требует пользовательского подтверждения перед использованием более слабого. Особенно коварный способ предпринять такую атаку MITM состоял бы в том, чтобы предложить "бесплатное" обслуживание кэширования на прокси-сервере легковерным пользователям.

15.3 Неправильное обращение с информацией файла регистрации сервера (Log)

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

15.4 Передача Секретной информации

Как любой универсальный протокол передачи данных, HTTP не может отрегулировать контент данных, которые переданы, и при этом нет никакого априорного метода определения чувствительности никакой определенной порции информации в пределах контекста никакого данного запроса. Поэтому, приложения SHOULD предоставляют так много контроля за этой информацией насколько возможно к провайдеру той информации. Четыре поля заголовка стоят специальное упоминание в этом контексте: Server, Via, Referer и From.

Раскрытие специфичной программной версии сервера может позволить серверу становиться более уязвимым для атак против программного обеспечения, которое, как известно, содержит бреши в защите. Разработчики ДОЛЖНЫ сделать поле заголовка Server конфигурируемой опцией.

Прокси, которые служат порталом через сетевую межсетевую защиту, ДОЛЖНЫ взять специальные предосторожности относительно передачи информации о заголовке, которая идентифицирует хосты позади межсетевой защиты. В частности они ДОЛЖНЫ удалить, или заменить санированными версиями, любые поля Via, сгенерированные позади межсетевой защиты.

Поле Referer позволяет читать образцы, которые будут изучены и обратные ссылки, которые рисуют. Хотя он может быть очень полезен, его мощность может быть неправильно эксплуатирована, если пользовательские детали не отделены от информации, содержавшейся в Referer. Даже когда персональная информация была удалена, поле Referer может указать документ private URI, публикация которого была бы несоответствующей.

Информация передала поле From, мог бы находиться в противоречии с интересами частной жизни пользователя или политикой безопасности их сайта, и следовательно он не ДОЛЖЕН быть передан без пользователя, являющегося способным отключить, допустить, и изменить содержание поля. Пользователь ДОЛЖЕН быть в состоянии установить содержание этого поля в пределах пользовательского предпочтения или прикладной конфигурации значений по умолчанию.

Мы предлагаем, хотя не требуют, чтобы удобный интерфейс переключателя был предоставлен для пользователя, чтобы допустить или отключить отправку информации Referer и From.

15.5 Атаки, основанные именах файлов и путей

Реализации серверов происхождения HTTP ДОЛЖНЫ делать все возможное ограничить документы, возвращенные запросами HTTP, чтобы быть только теми, которые были предназначены администраторами сервера. Если сервер HTTP переводит URI HTTP непосредственно в системные вызовы файла, сервер ДОЛЖЕН взять специальную заботу, чтобы не служить файлам, которые не были предназначены, чтобы быть поставленными клиентам HTTP. Например, UNIX, Microsoft Windows, и другие операционные системы используют ".." как компонент пути, чтобы указать каталог выравниваются выше текущего. На такой системе сервер HTTP ДОЛЖЕН отвергнуть любую такую конструкцию в Request-URI, если он иначе позволил бы доступ к ресурсу вне предназначенных быть доступным через сервер HTTP. Точно так же файлы, предназначенные для справочной информации только внутренне на сервер (например, файлы управления доступом, файлы конфигурации, и скриптовый код), ДОЛЖНЫ быть защищены от несоответствующего поиска, так как они могли бы содержать секретную информацию. Опыт показал тем незначительным ошибкам в таких реализациях сервера HTTP, превратились в угрозы безопасности.

15.6 Персональная Информация

Клиенты HTTP часто посвящены в большое количество персональной информации (например, имя пользователя, местоположение, отправляет по почте адрес, пароли, ключи шифрования, и т.д.), и ДОЛЖЕН очень делать все возможное предотвратить неумышленную утечку этой информации через протокол HTTP к другим источникам.

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

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

15.7 Проблемы секретности, связанные с Accept заголовками

Заголовки запроса Accept могут показать информацию о пользователе на все серверы, к которым обращаются. Заголовок Accept-Language в особенности может показать информацию, которую пользователь рассмотрел бы, чтобы быть характера private, потому что понимание определенных языков часто строго коррелируется к членству определенной этнической группы. Пользовательские агенты, которые предлагают опцию, чтобы конфигурировать содержание заголовка Accept-Language, который будет отправлен в каждом запросе, строго поощрены позволить процессу конфигурации включать сообщение, которое делает пользователя, знающего о потере частной жизни вовлеченный.

Подход, который ограничивает потерю частной жизни, был бы для user agent, чтобы опустить отправку заголовков Accept-Language по умолчанию, и спросить пользователя, должен ли он начать отправлять заголовки Accept-Language серверу, если он обнаруживает, ища любые поля заголовка ответа Vary, сгенерированные сервером, что такая отправка могла улучшить качество обслуживания.

Уточните настроенные пользователем поля заголовка ввода передали каждый запрос, в особенности если они включают качественные значения, может использоваться серверами как относительно надежные и долговечные пользовательские идентификаторы. Такие пользовательские идентификаторы позволили бы поставщикам оперативной информации делать прослеживание следа щелчка, и позволят сотрудничать поставщики оперативной информации, чтобы соответствовать следам щелчка поперечного сервера или представлениям формы индивидуальных пользователей. Обратите внимание, что для многих пользователей не позади прокси, сетевой адрес хоста, выполняющего user agent, будет также служить долговечным пользовательским идентификатором. В средах, где прокси используются, чтобы увеличить частную жизнь, пользовательские агенты должны быть консервативными в предложении опций конфигурации заголовка ввода конечным пользователям. Как критическая мера частной жизни, прокси могли фильтровать заголовки ввода в переданных запросах. Универсальные пользовательские агенты, которые предоставляют высокую степень конфигурируемости заголовка, должны предупредить пользователей о потере частной жизни, которая может быть вовлечена.

15.8 Подмена DNS-адресов (DNS Spoofing)

Клиенты, используя HTTP полагаются тяжело на Службу именования доменов, и являются таким образом обычно склонными к атакам безопасности, основанным на преднамеренной неправильной ассоциации имен DNS и адресов IP. Клиенты должны быть осторожными в принятии продолжающейся законности номера IP/DNS ассоциация имени.

В частности клиенты HTTP ДОЛЖНЫ положиться на свой преобразователь адресов имени для подтверждения номера IP/DNS ассоциация имени, вместо того, чтобы кэшировать результат предыдущих поисков имени хоста. Много платформ уже могут кэшировать поиски имени хоста локально когда приспособлено, и они ДОЛЖНЫ быть конфигурированы, чтобы сделать так. Эти поиски должны кэшироваться, однако, только когда ТТЛ-СХЕМА (Время, Чтобы Жить) информация, о которой сообщает блок преобразования имен, делает его вероятно, что кэшируемая информация останется полезной.

Если клиенты HTTP кэшируют результаты поисков имени хоста, чтобы достигнуть повышения производительности, они ДОЛЖНЫ наблюдать информацию о ТТЛ-СХЕМЕ, о которой сообщает DNS.

Если клиенты HTTP не наблюдают это правило, они могли бы быть spoofed, когда адрес IP ранее обращенного сервера изменяется. Поскольку сетевое изменение нумерации, как ожидают, все более и более станет распространено, возможность этой формы атаки будет расти. Наблюдение этого требования таким образом уменьшает это потенциальное уязвимое место безопасности.

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

15.9 Расположение заголовков и Spoofing

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

16. Подтверждения

Эта спецификация делает интенсивное использование увеличенной НОРМАЛЬНОЙ ФОРМЫ БЕКУСА-НАУРА и универсальных конструкций определенным Дэвидом H. Crocker для RFC 822. Точно так же он многократно использует многие из определений, предоставленных Nathaniel Borenstein и Недом Freed для MIME. Мы надеемся, что их включение в эту спецификацию поможет уменьшать прошлый беспорядок по связям между HTTP и интернет-форматами сообщения почты.

Протокол HTTP развился значительно за прошлые четыре года.

Он извлек выгоду из большого и активного разработчика community — много людей, которые участвовали на списке адресатов разговора WWW — и случается так, что community, который больше всего ответил за успехом HTTP и Международного Web вообще. Марк Andreessen, Роберт Cailliau, Дэниел W. Connolly, Боб Denny, Джон Franks, Жан-Francois Groff, Hallam-пекарь Филипа M., Hakon W. Ложь, Ari Luotonen, Rob McCool, Лу Montulli, Дейв Raggett, Тони Sanders, и Марк VanHeyningen заслуживают специального распознавания для их усилий в определении ранних аспектов протокола.

Этот документ принес пользу значительно из комментариев всех тем, которые участвуют в HTTP-WG. В дополнение к уже упомянутым следующие личности поспособствовали этой спецификации:

Gary Adams, Albert Lunde, Harald Tveit Alvestrand, John C. Mallery, Keith Ball, Jean-Philippe Martin-Flatin, Brian Behlendorf, Larry Masinter, Paul Burchard, Mitra, Maurizio Codogno, David Morris, Mike Cowlishaw, Gavin Nicol, Roman Czyborra, Bill Perry, Michael A. Dolan, Jeffrey Perry, David J. Fiander, Scott Powers, Alan Freier, Owen Rees, Marc Hedlund, Luigi Rizzo, Greg Herlihy, David Robinson, Koen Holtman, Marc Salomon, Alex Hopmann, Rich Salz, Bob Jernigan, Allan M. Schiffman, Shel Kaphan, Jim Seidman, Rohit Khare, Chuck Shotton, John Klensin, Eric W. Sink, Martijn Koster, Simon E. Spero, Alexei Kosut, Richard N. Taylor, David M. Kristol, Robert S. Thau, Daniel LaLiberte, Bill (BearHeart) Weinman, Ben Laurie, Francois Yergeau, Paul J. Leach, Mary Ellen Zurko, Daniel DuBois

Большая часть контента и представление кэширующего дизайна происходят из-за предложений и комментариев от личностей, включающих: Shel Kaphan, Пол Leach, Koen Holtman, Дэвид Morris, и Лэрри Masinter.

Большая часть спецификации диапазонов основана на работе, которая первоначально сделал Ari Luotonen и Джон Franks, с дополнительным вводом от Стива Zilles.

Благодаря "мужчинам пещеры" Альта Palo. Вы знаете, кто Вы.

Джим Gettys (текущий редактор этого документа) желает особенно благодарить Роя Fielding, предыдущий редактор этого документа, наряду с Джоном Klensin, Джефом Mogul, Полом Leach, Дейвом Kristol, Koen Holtman, Джоном Franks, Алексом Hopmann, и Лэрри Masinter для их справки.

17. Справочная информация

  1. Alvestrand, H., "Tags for the identification of languages", RFC 1766, UNINETT, March 1995.
  2. Anklesaria, F., McCahill, M., Lindner, P., Johnson, D., Torrey, D., and B. Alberti. "The Internet Gopher Protocol: (a distributed document search and retrieval protocol)", RFC 1436, University of Minnesota, March 1993.
  3. Berners-Lee, T., "Universal Resource Identifiers in WWW", A Unifying Syntax for the Expression of Names and Addresses of Objects on the Network as used in the World-Wide Web", RFC 1630, CERN, June 1994.
  4. Berners-Lee, T., Masinter, L., and M. McCahill, "Uniform Resource Locators (URL)", RFC 1738, CERN, Xerox PARC, University of Minnesota, December 1994.
  5. Berners-Lee, T., and D. Connolly, "HyperText Markup Language Specification — 2.0", RFC 1866, MIT/LCS, November 1995.
  6. Berners-Lee, T., Fielding, R., and H. Frystyk, "Hypertext Transfer Protocol — HTTP/1.0.", RFC 1945 MIT/LCS, UC Irvine, May 1996.
  7. Freed, N., and N. Borenstein, "Multipurpose Internet Mail Extensions (MIME) Part One: Format of Internet Message Bodies", RFC 2045, Innosoft, First Virtual, November 1996.
  8. Braden, R., "Requirements for Internet hosts — application and support", STD 3, RFC 1123, IETF, October 1989
  9. Crocker, D., "Standard for the Format of ARPA Internet Text Messages", STD 11, RFC 822, UDEL, August 1982.
  10. Davis, F., Kahle, B., Morris, H., Salem, J., Shen, T., Wang, R., Sui, J., and M. Grinbaum. "WAIS Interface Protocol Prototype Functional Specification", (v1.5), Thinking Machines Corporation, April 1990.
  11. Fielding, R., "Relative Uniform Resource Locators", RFC 1808, UC Irvine, June 1995.
  12. Horton, M., and R. Adams. "Standard for interchange of USENET messages", RFC 1036, AT&T Bell Laboratories, Center for Seismic Studies, December 1987.
  13. Kantor, B., and P. Lapsley. "Network News Transfer Protocol." A Proposed Standard for the Stream-Based Transmission of News", RFC 977, UC San Diego, UC Berkeley, February 1986.
  14. Moore, K., "MIME (Multipurpose Internet Mail Extensions) Part Three: Message Header Extensions for Non-ASCII Text", RFC 2047, University of Tennessee, November 1996.
  15. Nebel, E., and L. Masinter. "Form-based File Upload in HTML", RFC 1867, Xerox Corporation, November 1995.
  16. Postel, J., "Simple Mail Transfer Protocol", STD 10, RFC 821, USC/ISI, August 1982.
  17. Postel, J., "Media Type Registration Procedure", RFC 2048, USC/ISI, November 1996.
  18. Postel, J., and J. Reynolds, "File Transfer Protocol (FTP)", STD 9, RFC 959, USC/ISI, October 1985.
  19. Reynolds, J., and J. Postel, "Assigned Numbers", STD 2, RFC 1700, USC/ISI, October 1994.
  20. Sollins, K., and L. Masinter, "Functional Requirements for Uniform Resource Names", RFC 1737, MIT/LCS, Xerox Corporation, December 1994.
  21. US-ASCII. Coded Character Set — 7-Bit American Standard Code for Information Interchange. Standard ANSI X3.4-1986, ANSI, 1986.
  22. ISO-8859. International Standard — Information Processing — 8-bit Single-Byte Coded Graphic Character Sets — Part 1: Latin alphabet No. 1, ISO 8859-1:1987. Part 2: Latin alphabet No. 2, ISO 8859-2, 1987. Part 3: Latin alphabet No. 3, ISO 8859-3, 1988. Part 4: Latin alphabet No. 4, ISO 8859-4, 1988. Part 5: Latin/Cyrillic alphabet, ISO 8859-5, 1988. Part 6: Latin/Arabic alphabet, ISO 8859-6, 1987. Part 7: Latin/Greek alphabet, ISO 8859-7, 1987. Part 8: Latin/Hebrew alphabet, ISO 8859-8, 1988. Part 9: Latin alphabet No. 5, ISO 8859-9, 1990.
  23. Meyers, J., and M. Rose "The Content-MD5 Header Field", RFC 1864, Carnegie Mellon, Dover Beach Consulting, October, 1995.
  24. Carpenter, B., and Y. Rekhter, "Renumbering Needs Work", RFC 1900, IAB, February 1996.
  25. Deutsch, P., "GZIP file format specification version 4.3." RFC 1952, Aladdin Enterprises, May 1996.
  26. Venkata N. Padmanabhan and Jeffrey C. Mogul. Improving HTTP Latency. Computer Networks and ISDN Systems, v. 28, pp. 25-35, Dec. 1995. Slightly revised version of paper in Proc. 2nd International WWW Conf. '94: Mosaic and the Web, Oct. 1994, which is available at http://www.ncsa.uiuc.edu/SDG/IT94/Proceedings/DDay/mogul/HTTPLatency.html.
  27. Joe Touch, John Heidemann, and Katia Obraczka, "Analysis of HTTP Performance", http://www.isi.edu/lsam/ib/http-perf/, USC/Information Sciences Institute, June 1996
  28. Mills, D., "Network Time Protocol, Version 3, Specification, Implementation and Analysis", RFC 1305, University of Delaware, March 1992.
  29. Deutsch, P., "DEFLATE Compressed Data Format Specification version 1.3." RFC 1951, Aladdin Enterprises, May 1996.
  30. Spero, S., "Analysis of HTTP Performance Problems" URL:http://sunsite.unc.edu/mdma-release/http-prob.html.
  31. Deutsch, P., and J-L. Gailly, "ZLIB Compressed Data Format Specification version 3.3", RFC 1950, Aladdin Enterprises, Info-ZIP, May 1996.
  32. Franks, J., Hallam-Baker, P., Hostetler, J., Leach, P., Luotonen, A., Sink, E., and L. Stewart, "An Extension to HTTP : Digest Access Authentication", RFC 2069, January 1997.

18. Адреса Авторов

Roy T. Fielding
Department of Information and Computer Science
University of California
Irvine, CA 92717-3425, USA
Fax: +1 (714) 824-4056
EMail: ude.icu.sci@gnidleif

Jim Gettys
MIT Laboratory for Computer Science
545 Technology Square
Cambridge, MA 02139, USA
Fax: +1 (617) 258 8682
EMail: gro.3w@gj

Jeffrey C. Mogul
Western Research Laboratory
Digital Equipment Corporation
250 University Avenue
Palo Alto, California, 94305, USA
EMail: moc.ced.lrw@lugom

Henrik Frystyk Nielsen
W3 Consortium
MIT Laboratory for Computer Science
545 Technology Square
Cambridge, MA 02139, USA
Fax: +1 (617) 258 8682
EMail: gro.3w@kytsyrf

Tim Berners-Lee
Director, W3 Consortium
MIT Laboratory for Computer Science
545 Technology Square
Cambridge, MA 02139, USA
Fax: +1 (617) 258 8682
EMail: gro.3w@lbmit

19. Приложения

19.1 Медиа тип Интернет message/http

В дополнение к определению протокол HTTP/1.1, этот документ служит спецификацией для интернет-носителей type "message/http". Следующее должно быть регистрировано с IANA.

Media Type name:         message
Media subtype name:      http
Required parameters:     none
Optional parameters:     version, msgtype

 version: The HTTP-Version number of the enclosed message
          (e.g., "1.1"). If not present, the version can be
          determined from the first line of the body.

 msgtype: The message type -- "request" or "response". If not
          present, the type can be determined from the first
          line of the body.

Encoding considerations: only "7bit", "8bit", or "binary" are
                         permitted

Security considerations: none

19.2 Медиа тип Интернет multipart/byteranges

Когда сообщение HTTP включает контент множественных диапазонов (например, ответ на запрос на множественные ненакладывающиеся диапазоны), они переданы как многослойное сообщение MIME. Многослойный мультимедийный type с этой целью называют "multipart/byteranges".

multipart/byteranges мультимедийный type включает две или больше части, каждого с его собственными полями Content-Type И Content-Range. Части отделены, используя границу MIME parameter.

Media Type name:         multipart
Media subtype name:      byteranges
Required parameters:     boundary
Optional parameters:     none

Encoding considerations: only "7bit", "8bit", or "binary" are
                         permitted

Security considerations: none

Например:

HTTP/1.1 206 Partial content
Date: Wed, 15 Nov 1995 06:25:24 GMT
Last-modified: Wed, 15 Nov 1995 04:58:08 GMT
Content-type: multipart/byteranges; boundary=THIS_STRING_SEPARATES

--THIS_STRING_SEPARATES
Content-type: application/pdf
Content-range: bytes 500-999/8000

...the first range...
--THIS_STRING_SEPARATES
Content-type: application/pdf
Content-range: bytes 7000-7999/8000

...the second range
--THIS_STRING_SEPARATES--

19.3 Допустимые приложения

Хотя этот документ определяет требования генерации HTTP/1.1 сообщения, не, все приложения будут правильны в своей реализации. Мы поэтому рекомендуем, чтобы операционные приложения были терпимы к отклонениям всякий раз, когда те отклонения могут быть интерпретированы однозначно.

Клиенты ДОЛЖНЫ быть терпимыми в парсинге Линии состояния и серверов, терпимых, разбирая Линию запроса. В частности они ДОЛЖНЫ принять любое количество символов SP ИЛИ HT между полями, даже при том, что только отдельная ИСПАНИЯ требуется.

Признак конца линии для полей заголовка сообщения — последовательность CRLF.

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

Символьный набор тела объекта не должен быть маркирован как самый низкий общий знаменатель символьных кодов, используемых в пределах того тела, за исключением того, что никакой, метка предпочтена по меткам US-ASCII или ISO-8859-1.

Дополнительные правила для требований при парсинге и кодировании дат и других потенциальных проблем с кодированиями даты включают:

19.4 Различия между HTTP и MIME объектами

HTTP/1.1 использует многие из конструкций, определенных для интернет-Почты (RFC 822) и MIME (MIME), чтобы позволить объектам быть переданными в открытом разнообразии представлений и с расширяемыми механизмами. Однако, MIME [7] обсуждает почту, и у HTTP есть несколько возможностей, которые отличаются от описанных в MIME. Эти различия были тщательно выбраны, чтобы оптимизировать производительность по двоичным подключениям, позволить большую свободу в использовании новых типов информации, сделать сравнения даты более простыми, и признать практику некоторых ранних серверов HTTP и клиентов.

Это приложение описывает специфичные области, где HTTP отличается от MIME. Прокси и шлюзы к строгим средам MIME ДОЛЖНЫ знать об этих различиях и предоставлять соответствующие преобразования где необходимо. Прокси и шлюзы от сред MIME до HTTP также должны знать о различиях, потому что могут требоваться некоторые преобразования.

19.4.1 Преобразование к канонической форме

MIME требует, чтобы интернет-объект почты преобразовали в каноническую форму до того, чтобы быть переданным. Раздел 3.7.1 этого документа описывает формы, учитывал подтипы "текстового" мультимедийного type когда передано по HTTP. MIME требует, чтобы контент с type "текста" представил концы строки как CRLF, и запрещает использование CR или перевода строки за пределами последовательностей конца строки. HTTP позволяет CRLF, пустому CR, и пустому переводу строки указывать конец строки в пределах текстового контента, когда сообщение передано по HTTP.

Где он возможен, прокси или шлюз от HTTP до строгой среды MIME ДОЛЖНЫ перевести все концы строки в пределах текстовых типов информации, описанных в разделе 3.7.1 этого документа канонической форме MIME CRLF. Обратите, однако, внимание, что это может быть сложно присутствием Content-Encoding и фактом, что HTTP позволяет использование некоторых наборов символов, которые не используют октеты 13 и 10, чтобы представить CR и перевод строки, как имеет место для некоторых многобайтовых наборов символов.

19.4.2 Преобразование форматов Date

HTTP/1.1 использует ограниченный набор форматов даты (раздел 3.3.1), чтобы упростить процесс сравнения даты. Прокси и шлюзы из других протоколов ДОЛЖНЫ гарантировать, что любое поле заголовка Date, существующее в сообщении, соответствует одному из HTTP/1.1 форматы и перезаписывать дату в случае необходимости.

19.4.3 Введение Content-Encoding

MIME не включает понятия, эквивалентного полю заголовка/1.1 HTTP ContentEncoding. Так как это действует как модификатор на мультимедийном type, прокси и шлюзы от HTTP до совместимых MIME протоколов ДОЛЖНЫ или изменить значение поля заголовка Content-Type или декодировать тело объекта прежде, чем отправить сообщение. (Некоторые экспериментальные приложения Content-Type для интернет-почты использовали media-type parameter "; преобразования = <content-coding>", чтобы выполнить эквивалентную функцию как Content-Encoding. Однако, этот parameter не часть MIME).

19.4.4 Никакого Content-Transfer-Encoding

HTTP не использует поле Content-Transfer-Encoding (CTE) MIME.

Прокси и шлюзы от совместимых MIME протоколов до HTTP ДОЛЖНЫ удалить любое не-identity CTE ("quoted-printable" или "base64") кодирование до поставки ответного сообщения клиенту HTTP.

Прокси и шлюзы от HTTP до совместимых MIME протоколов должны гарантировать, что сообщение находится в правильном формате и кодировании для безопасного транспорта на том протоколе, где "безопасный транспорт" определен ограничениями используемого протокола.

Такой прокси или шлюз ДОЛЖНЫ маркировать данные соответствующим Content-Transfer-Encoding, если выполнение так улучшит вероятность безопасного транспорта по протоколу адресата.

19.4.5 Поля HTTP заголовка в Multipart Body-Parts

В MIME обычно игнорируется большинство полей заголовка в многослойном body-parts, если имя поля не начинается "с Content-". В HTTP/1.1, многослойный body-parts может содержать любые поля заголовка HTTP, которые существенны для значения той части.

19.4.6 Введение Transfer-Encoding

HTTP/1.1 представляет поле заголовка Transfer-Encoding (раздел 14.40). Прокси/шлюзы ДОЛЖНЫ удалить любое кодирование передачи до пересылки сообщения через совместимый MIME протокол.

Процесс для того, чтобы декодировать кодирование передачи "chunked" (раздел 3.6) может быть представлен в псевдокоде как:

length := 0
read chunk-size, chunk-ext (if any) and CRLF
while (chunk-size > 0) {
   read chunk-data and CRLF
   append chunk-data to entity-body
   length := length + chunk-size
   read chunk-size and CRLF
}
read entity-header
while (entity-header not empty) {
   append entity-header to existing header fields
   read entity-header
}
Content-Length := length
Remove "chunked" from Transfer-Encoding

19.4.7 Версия MIME

HTTP не совместимый MIME протокол (см. приложение 19.4). Однако, HTTP/1.1 сообщения может включить отдельное общее поле заголовка MIME-Version, чтобы указать, какая версия протокола MIME использовалась, чтобы создать сообщение. Использование поля заголовка MIME-Version указывает, что сообщение находится в полном согласии с протоколом MIME.

Прокси/шлюзы должны гарантировать полное согласие (где только возможно), экспортируя сообщения HTTP в строгие среды MIME.

MIME-Version   = "MIME-Version" ":" 1*DIGIT "." 1*DIGIT

Версия MIME "1.0" является значением по умолчанию для использования в HTTP/1.1. Однако, HTTP/1.1 парсинг сообщения и семантика определен в соответствии с этим документом а не спецификацией MIME.

19.5 Изменения относительно HTTP/1.0

Этот раздел суммирует главные различия между версиями HTTP/1.0 и HTTP/1.1.

19.5.1 Изменения упрощаущие много-homed сервера и сохраняющие IP адреса

Требования, чтобы клиенты и серверы поддержали Host requestheader, сообщают об ошибке, если заголовок запроса Host (раздел 14.23) пропускает от HTTP/1.1 запрос, и принимать абсолютные URI (раздел 5.1.2) среди самых важных изменений, определенных этой спецификацией.

Старший HTTP/1.0 клиенты предполагал взаимно-однозначные связи адресов IP и серверов; не было никакого другого установленного механизма для того, чтобы отличить намеченный сервер запроса чем адрес IP, к которому был направлен тот запрос. Изменения, выделенные выше, позволят Интернет, когда-то старшие клиенты HTTP больше не распространены, поддерживать множественные Web-сайты от отдельного адреса IP, значительно упрощая большие операционные Web-серверы, где выделение многих адресов IP к отдельному хосту создало серьезные проблемы. Интернет также будет в состоянии возвратить адреса IP, которые были распределены в единственной цели позволить, что имена домена специального назначения, которые будут использоваться в root — выравнивают HTTP URL. Учитывая норму роста Web, и числа серверов уже развертывался, чрезвычайно важно, что все реализации HTTP (включение обновления существующего HTTP/1.0 приложения) правильно реализуют эти требования:

19.6 Дополнительные возможности

Эти элементы протокола документов приложения, используемые некоторыми существующими реализациями HTTP, но не последовательно и правильно через большинство HTTP/1.1 приложения. Разработчики должны знать об этих возможностях, но не могут положиться на их присутствие в, или функциональная совместимость с, другой HTTP/1.1 приложения. Некоторые из них описывают предложенные экспериментальные возможности, и некоторые описывают возможности, что экспериментальное развертывание нашло недостаток, к которым теперь обращаются в основном HTTP/1.1 спецификация.

19.6.1 Дополнительные методы запросов

19.6.1.1 PATCH

Метод PATCH похож на PUT за исключением того, что объект содержит список различий между оригинальной версией ресурса, идентифицированного Request-URI и заданным контентом ресурса после того, как действие PATCH было применено. Список различий находится в формате, определенном мультимедийным type объекта (например, "приложение/разность"), и ДОЛЖЕН включить достаточную информацию, чтобы позволить серверу обновлять изменения, необходимые, чтобы конвертировать оригинальную версию ресурса к заданной версии.

Если запрос проходит через кэш, и Request-URI идентифицирует в настоящий момент кэшируемый объект, тот объект ДОЛЖЕН быть удален из кэша. Ответы на этот метод не cachable.

Фактический метод для того, чтобы определить, как исправленный ресурс помещен, и что случается с его предшественником, определен полностью сервером происхождения. Если бы оригинальная версия исправляемого ресурса включала поле заголовка Content-Version, то объект запроса ДОЛЖЕН включить поле заголовка Derived-From, соответствующее значению оригинала поле заголовка Content-Version. Приложения поощрены использовать эти поля для того, чтобы создать связи управления версиями и разрешить конфликты версии.

Запросы PATCH должны повиноваться требованиям передачи сообщения, изложенным в разделе 8.2.

Кэши, которые реализуют PATCH, должны лишить кэшируемые ответы законной силы как определено в разделе 13.10 для PUT.

19.6.1.2 LINK

Метод LINK устанавливает одни или более связей Ссылки между существующим ресурсом, идентифицированным Request-URI и другими существующими ресурсами. Различие между LINK и другими методами, позволяющими ссылки быть установленными между ресурсами, — то, что метод LINK не позволяет никакому телу сообщения быть отправленным в запросе и непосредственно не заканчивается созданием новых ресурсов.

Если запрос проходит через кэш, и Request-URI идентифицирует в настоящий момент кэшируемый объект, тот объект ДОЛЖЕН быть удален из кэша. Ответы на этот метод не cachable.

Кэши, которые реализуют LINK, должны лишить кэшируемые ответы законной силы как определено в разделе 13.10 для PUT.

19.6.1.3 UNLINK

Метод UNLINK удаляет одни или более связей Ссылки из существующего ресурса, идентифицированного Request-URI. Эти связи, возможно, были установлены, используя метод LINK или любым другим методом, поддерживающим заголовок Ссылки. Удаление ссылки к ресурсу не подразумевает, что ресурс прекращает существовать или становится недоступным для будущей справочной информации.

Если запрос проходит через кэш, и Request-URI идентифицирует в настоящий момент кэшируемый объект, тот объект ДОЛЖЕН быть удален из кэша. Ответы на этот метод не cachable.

Кэши, которые реализуют UNLINK, должны лишить кэшируемые ответы законной силы как определено в разделе 13.10 для PUT.

19.6.2 Дополнительные определения полей заголовка

19.6.2.1 Замены

Поле заголовка ответа Замен было предложено как средство для сервера происхождения, чтобы сообщить клиенту о других доступных представлениях запрошенного ресурса, наряду с их различением атрибутов, и таким образом предоставлением более надежного средства для user agent, чтобы выполнить последующий выбор другого представления, которое лучше соответствует желаниям его пользователя (описанный как управляемые агентом переговоры в разделе 12). Поле заголовка Замен является ортогональным к полю заголовка Vary в том, оба могут сосуществовать в сообщении, не затрагивая интерпретацию ответа или доступных представлений. Ожидается, что Замены предоставят существенное усовершенствование по управляемым сервером переговорам, предоставленным полем Vary для тех ресурсов, которые изменяются по общим размерностям как type и язык.

Поле заголовка Замен будет определено в будущей спецификации.

19.6.2.2 Content-Version

Поле заголовка объекта Content-Version определяет тэг версии, связанный с преобразованной копией развивающегося объекта. Вместе с полем Derived-From, описанным в разделе 19.6.2.3, он позволяет группе людей работать одновременно при создании работы как итерационный процесс. Поле должно использоваться, чтобы позволить развитие определенной работы вдоль отдельного пути, а не полученных работ или преобразованных копий в других представлениях.

Content-Version = "Content-Version" ":" quoted-string

Примеры поля Content-Version включают:

Content-Version: "2.1.2"
Content-Version: "Fred 19950116-12:26:48"
Content-Version: "2.5a4-omega7"

19.6.2.3 Derived-From

Поле заголовка объекта Derived-From может использоваться, чтобы указать тэг версии ресурса, из которого был получен включенный объект прежде, чем модификации были сделаны отправителем. Это поле используется, чтобы помочь управлять процессом объединения последовательных изменений ресурса, особенно когда такие изменения производятся параллельно и из множественных источников.

Derived-From   = "Derived-From" ":" quoted-string

Приведенное в качестве примера использование поля:

Derived-From: "2.1.1"

Поле Derived-From требуется для PUT и запросов PATCH, если отправляемый объект был ранее найден от того же самого URI, и заголовок Content-Version был включен в объект, когда он был последний найденный.

19.6.2.4 Ссылка

Поле заголовка объекта Ссылки предоставляет средство для того, чтобы описать связи между двумя ресурсами, обычно между запрошенным ресурсом и некоторым другим ресурсом. Объект МОЖЕТ включить множественные значения Link. Ссылки на уровне метаинформации обычно указывают связи как иерархическая структура и навигационные пути. Поле Link семантически эквивалентно <LINK> элемент в HTML. [5]

Link           = "Link" ":" #("<" URI ">" *( ";" link-param )

link-param     = ( ( "rel" "=" relationship )
                   | ( "rev" "=" relationship )
                   | ( "title" "=" quoted-string )
                   | ( "anchor" "=" <"> URI <"> )
                   | ( link-extension ) )

link-extension = token [ "=" ( token | quoted-string ) ]

relationship   = sgml-name
               | ( <"> sgml-name *( SP sgml-name) <"> )

sgml-name      = ALPHA *( ALPHA | DIGIT | "." | "-" )

Значения связей являются независящими от регистра и МОГУТ распространяться в пределах ограничений синтаксиса sgml-имени. parameter заголовка МОЖЕТ использоваться, чтобы маркировать адресата ссылки таким образом, что он может использоваться как идентификация в пределах удобочитаемого меню. Привязка parameter МОЖЕТ использоваться, чтобы указать исходную привязку кроме всего текущего ресурса, например, фрагмент этого ресурса или третьего ресурса.

Примеры использования включают:

Link: <http://www.cern.ch/TheBook/chapter2>; rel="Previous"

Link: <mailto:timbl@w3.org>; rev="Made"; title="Tim Berners-Lee"

Первый пример указывает, что chapter2 до этого ресурса в логическом навигационном пути. Второе указывает, что человек, ответственный за то, что делал доступный ресурс, идентифицирован данным почтовым адресом.

19.6.2.5 URI

Поле заголовка URI, в прошлых версиях этой спецификации, использовалось как комбинация существующего Location, ContentLocation, и полей заголовка Vary, а также будущего поля Alternates (выше). Его первичная цель состояла в том, чтобы включить список дополнительных URI для ресурса, включая местоположения зеркала и имена. Однако, он стал ясным, что комбинация многих других функций в пределах этого отдельного поля была барьером к последовательно и правильно реализующий любую из тех функций.

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

URI-header    = "URI" ":" 1#( "<" URI ">" )

19.7 Совместимость с предыдущими версиями

Он выходит за рамки спецификации протокола, чтобы передать под мандат согласие с предыдущими версиями. HTTP/1.1 был преднамеренно проектирован, однако, сделать поддерживающие предыдущие версии простыми. Он стоит отмечать, что во время создания этой спецификации, мы ожидали бы коммерческий HTTP/1.1 серверы:

И мы ожидали бы HTTP/1.1 клиенты:

Для большинства реализаций HTTP/1.0, каждое подключение установлено клиентом до запроса и закрыто сервером после отправки ответа. Несколько реализаций реализуют версию Keep-Alive постоянных подключений, описанных в разделе 19.7.1.1.

19.7.1 Совместимость с постоянными соединениями, определяемыми HTTP/1.0

Некоторые клиенты и серверы могут желать быть совместимыми с некоторыми предыдущими реализациями постоянных подключений в HTTP/1.0 клиенты и серверы. О постоянных подключениях в HTTP/1.0 нужно явно договориться, поскольку они не поведение значения по умолчанию. HTTP/1.0 экспериментальные реализации постоянных подключений является дефектным, и новые средства в HTTP/1.1 проектированы, чтобы исправить эти проблемы. Проблема состояла в том, что некоторые существующие 1.0 клиента могут отправлять Keep-Alive прокси-серверу, который не понимает Connection, который тогда ошибочно отправил бы его следующему прибывающему серверу, который установит подключение Keep-Alive и результат в зависнувшем HTTP/1.0 прокси, ждущий близкого на ответе. Результат состоит в том, что HTTP/1.0 клиенты должен быть предотвращен от использования Keep-Alive когда говорящий с прокси.

Однако, говоря с прокси самое важное использование постоянных подключений, так, чтобы запрещение было ясно недопустимо. Поэтому, мы нуждаемся в некотором другом механизме для того, чтобы указать, что постоянное подключение задано, который безопасен использовать, даже когда говорящий со старым прокси, который игнорирует Connection. Постоянные подключения — значение по умолчанию для HTTP/1.1 сообщения; мы представляем новое ключевое слово (Connection: близко) для того, чтобы объявить непостоянство.

Следующее описывает оригинал HTTP/1.0 форма постоянных подключений.

Когда он подключается к серверу происхождения, клиент HTTP МОЖЕТ отправить Keep-Alive connection-token в дополнение к Сохранению connectiontoken:

Connection: Keep-Alive

HTTP/1.0 сервер тогда ответил бы подключением Keep-Alive, которое token и клиент могут продолжить с HTTP/1.0 (или Keep-Alive) постоянное подключение.

HTTP/1.1 сервер может также установить постоянные подключения с HTTP/1.0 клиенты по получении подключения Keep-Alive token.

Однако, постоянное подключение с HTTP/1.0 клиент не может использовать chunked кодирование передачи, и поэтому ДОЛЖНО использовать Content-Length для того, чтобы отметить заканчивающуюся границу каждого сообщения.

Клиент не ДОЛЖЕН отправить подключению Keep-Alive token прокси-серверу, поскольку HTTP/1.0 прокси-серверы не повинуется правилам HTTP/1.1 для того, чтобы разобрать поле заголовка Connection.

19.7.1.1 Заголовок Keep-Alive

Когда Keep-Alive, connection-token был передан с запросом или ответом, поле заголовка Keep-Alive, МОЖЕТ также быть включен. Поле заголовка Keep-Alive принимает следующую форму:

Keep-Alive-header = "Keep-Alive" ":" 0# keepalive-param

keepalive-param = param-name "=" value

Заголовок самого Keep-Alive является опциональным, и используется, только если parameter отправляют. HTTP/1.1 не определяет параметров.

Если заголовок Keep-Alive отправляют, соответствующее подключение, token ДОЛЖЕН быть передан. Заголовок Keep-Alive ДОЛЖЕН быть проигнорирован если получено без подключения token.

Перевод на русский язык

Алексей Симонов, moc.ksmo@kihsel