Пользовательские заголовки HTTP: соглашения об именах
Некоторые из наших пользователей попросили нас включить данные, относящиеся к их учетной записи, в заголовки HTTP запросов, которые мы им отправляем, или даже ответы, которые они получают от нашего API. Каково общее соглашение для добавления пользовательских заголовков HTTP, с точки зрения именования, формата... и т. Д.
Кроме того, не стесняйтесь публиковать любые умные их использования, которые вы наткнулись в Интернете; Мы пытаемся реализовать это, используя в качестве цели то, что лучше всего:)
6 ответов
В июне 2012 года рекомендация об использовании префикса "X-" стала официальной как RFC 6648. Ниже приведены ссылки на актуальность:
3. Рекомендации для создателей новых параметров
...
- НЕ СЛЕДУЕТ ставить перед именами их параметров "X-" или подобные конструкции.
4. Рекомендации для разработчиков протоколов
...
НЕ ДОЛЖЕН запрещать регистрацию параметров с префиксом "X-" или аналогичных конструкций.
НЕ ДОЛЖНО оговариваться, что параметр с префиксом "X-" или аналогичными конструкциями следует понимать как нестандартный.
НЕ ДОЛЖЕН оговариваться, что параметр без префикса "X-" или аналогичных конструкций должен пониматься как стандартизированный.
Обратите внимание, что "НЕ ДОЛЖНО" ("не рекомендуется") не то же самое, что "НЕ ДОЛЖНО" ("запрещено"), см. Также RFC 2119 для другой спецификации по этим ключевым словам. Другими словами, вы можете продолжать использовать заголовки с префиксом "X-", но это не рекомендуется, и вы не можете документировать их, как если бы они были общедоступными стандартами.
В июне 2011 года был опубликован первый черновик IETF, в котором не рекомендуется использовать префикс "X-" для нестандартных заголовков. Причина в том, что когда нестандартные заголовки с префиксом "X-" становятся стандартными, удаление префикса "X-" нарушает обратную совместимость, заставляя прикладные протоколы поддерживать оба имени (например, x-gzip
& gzip
сейчас эквивалентны). Таким образом, рекомендация состоит в том, чтобы просто назвать их разумно без префикса "X-".
Рекомендация состояла в том, чтобы начать их имя с "X-". Например X-Forwarded-For
, X-Requested-With
, Это также упоминается в разделе 5 RFC 2047.
Вопрос стоит перечитать. Заданный вопрос не похож на префиксы поставщиков в свойствах CSS, где уместно ориентироваться на будущее и думать о поддержке поставщиков и официальных стандартах. Фактический вопрос больше похож на выбор имен параметров запроса URL. Никого не должно волновать, кто они. Но использование именных интервалов является вполне допустимым - и распространенным, и правильным - делом.
Обоснование:
Речь идет о соглашениях между разработчиками для пользовательских, специфичных для приложения заголовков - "данных, относящихся к их учетной записи" - которые не имеют ничего общего с поставщиками, органами стандартизации или протоколами, которые должны быть реализованы третьими сторонами, за исключением того, что данный разработчик находится под вопросом просто необходимо избегать имен заголовков, которые могут использоваться другими серверами, прокси-серверами или клиентами. По этой причине приведенные примеры "X-Gzip/Gzip" и "X-Forwarded-For/Forwarded-For" являются спорными. Поставленный вопрос касается соглашений в контексте частного API, схожего с соглашениями об именах параметров запроса URL. Это вопрос предпочтения и расстояния между именами; опасения по поводу того, что "X-ClientDataFoo" поддерживается любым прокси-сервером или поставщиком без "X", явно неуместны.
В префиксе "X-" нет ничего особенного или волшебного, но это помогает прояснить, что это пользовательский заголовок. Фактически, RFC-6648 и др. Помогают подкрепить аргументы в пользу использования префикса "X-", потому что - поскольку производители HTTP-клиентов и серверов отказываются от префикса - от вашего приложения, частного API, личных данных - Механизм передачи становится еще лучше изолированным от столкновений пространства имен с небольшим количеством официальных зарезервированных имен заголовков. Тем не менее, мое личное предпочтение и рекомендация - пойти дальше и сделать, например, "X-ACME-ClientDataFoo" (если ваша компания по производству виджетов - "ACME").
ИМХО спецификация IETF недостаточно конкретна, чтобы ответить на вопрос OP, потому что она не может различить совершенно разные варианты использования: (A) поставщики вводят новые глобально применимые функции, такие как "Forwarded-For", с одной стороны, против (B) разработчики приложений передают специфичные для приложения строки клиенту и серверу. Спецификация касается только первого, (A). Вопрос здесь в том, существуют ли соглашения для (B). Есть. Они включают в себя группировку параметров в алфавитном порядке и отделение их от множества соответствующих стандартам заголовков типа (A). Использование префикса "X-" или "X-ACME-" удобно и допустимо для (B) и не конфликтует с (A). Чем больше вендоров прекратят использовать "X-" для (A), тем более отчетливыми станут (B).
Пример:
Google (который имеет небольшой вес в различных органах стандартизации) - по состоянию на сегодня 2014-1102 в этом небольшом редактировании моего ответа - в настоящее время использует "X-Mod-Pagespeed", чтобы указать версию своего модуля Apache, участвующего в преобразование данного ответа. Кто-нибудь действительно предлагает, чтобы Google использовал "Mod-Pagespeed" без "X-" и / или попросил IETF благословить его использование?
Резюме:
Если вы используете пользовательские заголовки HTTP (в качестве иногда подходящей альтернативы файлам cookie) в своем приложении для передачи данных на сервер или с него, и эти заголовки явно НЕ предназначены для использования вне контекста вашего приложения, Интервал между именами с префиксом "X-" или "X-FOO-" является разумным и распространенным соглашением.
Формат заголовков HTTP определен в спецификации HTTP. Я собираюсь поговорить о HTTP 1.1, для которого спецификация RFC 2616. В разделе 4.2 "Заголовки сообщений" определена общая структура заголовка:
message-header = field-name ":" [ field-value ]
field-name = token
field-value = *( field-content | LWS )
field-content = <the OCTETs making up the field-value
and consisting of either *TEXT or combinations
of token, separators, and quoted-string>
Это определение опирается на два основных столпа, токен и текст. Оба они определены в разделе 2.2 "Основные правила". Токен это:
token = 1*<any CHAR except CTLs or separators>
В свою очередь опираясь на CHAR, CTL и разделители:
CHAR = <any US-ASCII character (octets 0 - 127)>
CTL = <any US-ASCII control character
(octets 0 - 31) and DEL (127)>
separators = "(" | ")" | "<" | ">" | "@"
| "," | ";" | ":" | "\" | <">
| "/" | "[" | "]" | "?" | "="
| "{" | "}" | SP | HT
ТЕКСТ это:
TEXT = <any OCTET except CTLs,
but including LWS>
Где LWS - линейный пробел, определение которого я не буду воспроизводить, а OCTET:
OCTET = <any 8-bit sequence of data>
Есть примечание, сопровождающее определение:
The TEXT rule is only used for descriptive field contents and values
that are not intended to be interpreted by the message parser. Words
of *TEXT MAY contain characters from character sets other than ISO-
8859-1 [22] only when encoded according to the rules of RFC 2047
[14].
Итак, два вывода. Во-первых, ясно, что имя заголовка должно состоять из подмножества символов ASCII - буквенно-цифровых символов, некоторой пунктуации, а не чего-то еще. Во-вторых, в определении значения заголовка нет ничего, что ограничивало бы его ASCII или исключало бы 8-битные символы: оно явно состоит из октетов, только с запрещенными управляющими символами (обратите внимание, что CR и LF считаются элементами управления). Кроме того, комментарий к продукции TEXT подразумевает, что октеты должны интерпретироваться как находящиеся в ISO-8859-1, и что существует механизм кодирования (который, кстати, ужасен) для представления символов вне этой кодировки.
Поэтому, в частности, для ответа на @BalusC совершенно ясно, что согласно спецификации значения заголовков приведены в ISO-8859-1. Я отправил символы высокого уровня 8859-1 (в частности, некоторые акцентированные гласные, как они используются на французском языке) в заголовке из Tomcat, и правильно интерпретировал их Firefox, так что в некоторой степени это работает на практике так же, как и в теории (хотя это был заголовок Location, который содержит URL, и эти символы недопустимы в URL, так что это было фактически недопустимо, но по другому правилу!).
Тем не менее, я бы не стал полагаться на ISO-8859-1, работающий на всех серверах, прокси и клиентах, поэтому я бы придерживался ASCII в качестве защитного программирования.
RFC6648 рекомендует, чтобы вы предположили, что ваш пользовательский заголовок "может стать стандартизированным, общедоступным, широко развернутым или использоваться в нескольких реализациях". Поэтому он рекомендует не ставить перед ним префикс "X-" или подобные конструкции.
Однако есть исключение "когда крайне маловероятно, что [ваш заголовок] когда-либо будет стандартизирован". Для таких заголовков "для конкретной реализации и частного использования" RFC говорит, что пространство имен, такое как префикс поставщика, является оправданным.
Изменение, или, вернее, добавление дополнительных заголовков HTTP - отличный инструмент для отладки кода, если ничего больше.
Когда URL-запрос возвращает перенаправление или изображение, отсутствует html-страница для временной записи результатов кода отладки, по крайней мере, той, которая видна в браузере.
Один из подходов состоит в том, чтобы записать данные в локальный файл журнала и просмотреть этот файл позже. Другой способ - временно добавить заголовки HTTP, отражающие отлаживаемые данные и переменные.
Я регулярно добавляю дополнительные HTTP-заголовки, такие как X-fubar-somevar: или X-testing-someresult: чтобы проверить это, - и обнаружил множество ошибок, которые в противном случае было бы очень трудно отследить.
Реестр имен полей заголовков определен в RFC3864, и ничего особенного в "X-" нет.
Насколько я могу судить, нет никаких указаний для частных заголовков; сомневаюсь, избегай их. Или взгляните на HTTP Extension Framework ( RFC 2774).
Было бы интересно понять больше варианта использования; почему нельзя добавить информацию в тело сообщения?