Назад | Перейти на главную страницу

Nginx игнорирует клиентский запрос HTTP 1.0 и отвечает по HTTP 1.1

Я тестирую с помощью nginx/php5-fpm, с кодом

<?php

header($_SERVER["SERVER_PROTOCOL"]." 404 Not Found"); 
// also tested: header("Status: 404 Not Found");

echo $_SERVER["SERVER_PROTOCOL"];

И заставить использовать HTTP 1.0 с curl команда.

curl -0 -v 'http://www.example.com/test.php'


> GET /test.php HTTP/1.0

< HTTP/1.1 404 Not Found
< Server: nginx
< Date: Sat, 27 Oct 2012 08:51:27 GMT
< Content-Type: text/html
< Connection: close
< 
* Closing connection #0
HTTP/1.0

Как видите, я уже запрашиваю использование HTTP 1.0, но nginx ответил мне HTTP 1.1

Щедрость

@MaximDounin, @MichaelHampton уже предоставили ответ на спецификацию, спасибо. Я немного расширяю этот вопрос для будущего читателя:

В. Каковы преимущества ответа HTTP 1.1, когда клиент запрашивает HTTP 1.0? Разве подход Google не должен быть более разумным, т.е. когда клиент запрашивает 1.0, а отвечает 1.0?

Это нормальное и ожидаемое поведение, согласно RFC 2616:

Приложения, которые хотя бы условно соответствуют этой спецификации, ДОЛЖНЫ использовать HTTP-версию «HTTP / 1.1» в своих сообщениях и ДОЛЖНЫ делать это для любого сообщения, несовместимого с HTTP / 1.0. Дополнительные сведения о том, когда отправлять определенные значения HTTP-версии, см. В RFC 2145.

RFC 2145 расширяет это:

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

HTTP-сервер МОЖЕТ отправить более низкую версию ответа, если известно или подозревается, что клиент неправильно реализует спецификацию HTTP, но это не должно быть по умолчанию, и это НЕ СЛЕДУЕТ делать, если версия запроса - HTTP / 1.1 или выше.

На английском это означает следующее: если клиент отправляет запрос HTTP / 1.0, приемлем ответ HTTP / 1.0 или HTTP / 1.1, но предпочтительнее HTTP / 1.1.

Причина, по которой это делается, заключается в том, что один конец может рекламировать самую высокую версию HTTP, которую он может поддерживать, чтобы другой конец мог выбрать обновление поддержки своего протокола (если это возможно). Оба конца затем решат, с какой версией протокола они могут жить. Этот дизайн также помогает справиться с ошибками реализации, как указано в RFC 2145.

В то время также предполагалось, что могут быть и другие версии протокола HTTP, как второстепенные, так и основные версии, а правила предназначались для обеспечения совместимости. Неосведомленный Google о RFC может однажды сломаться HTTP / 2.0 дорабатывается. (Вы знаете его в черновой форме как SPDY.)

В. Каковы преимущества ответа HTTP 1.1, когда клиент запрашивает HTTP 1.0?

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

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

"Эй, я знаю, что вы отправили мне запрос, используя HTTP / 1.0, но просто чтобы вы знали, что я AM поддерживает HTTP /1.1. и вот ответ на ваш исходный запрос: [..]"

(Примечание: если сервер поддерживает вымышленный HTTP / 1.8, он ответит этим.)

Это избавляет вас от дополнительных запросов в некоторых ситуациях. Если вам нужно ПОЛУЧИТЬ 3 разных URI с сервера, вы можете отправить первый как HTTP / 1.0, а затем перейти к самой высокой версии, которую вы и сервер поддерживаете для последующих запросов.