HTTP конвейерная обработка - одновременные ответы на соединение
Я только что читал эту статью в Википедии, посвященную конвейерной обработке HTTP, и из диаграммы видно, что ответы могут отправляться одновременно по одному соединению. Я неправильно интерпретирую диаграмму или это разрешено?
Раздел 8.1.2.2 RFC 2616 гласит:
Сервер ДОЛЖЕН отправить свои ответы на эти запросы в том же порядке, в котором они были получены.
Хотя это и не исключает явного исключения одновременных ответов, в нем не упоминается необходимость обеспечения того, чтобы ответы начинались не только в правильном порядке по отношению к запросам, но и заканчивались в правильном порядке.
Я также не могу себе представить практичность работы с параллельными ответами - как бы клиент узнал, к какому ответу применяются полученные данные?
Поэтому моя интерпретация RFC заключается в том, что хотя дополнительные запросы могут быть сделаны во время обработки ответа на первый запрос, клиенту не разрешается отправлять параллельные запросы или серверу отправлять параллельные ответы по одному и тому же соединению.
Это правильно? Я приложил диаграмму ниже, чтобы проиллюстрировать мою интерпретацию.
Это предотвратит возникновение проблем, о которых я говорил, но, похоже, не полностью соответствует диаграмме в Википедии.
1 ответ
Краткий ответ: Да, клиенты и серверы могут отправлять запросы и ответы одновременно.
Однако сервер не может отправить несколько ответов на один запрос, т.е. шаблон ответа на запрос все еще применяется. RFC 2616 (и статья в Википедии, на которую вы ссылаетесь) просто заявляют, что клиенту не нужно ждать ответа сервера, чтобы отправить дополнительный запрос по тому же соединению. Таким образом, запросы в вашей диаграмме выглядят хорошо:).
Но серверу не нужно ждать окончания каждого из своих ответов, прежде чем он сможет начать передачу следующего ответа. Он может просто отправлять ответы клиенту, когда он получает запросы клиента. (Который приводит к диаграмме, показанной в статье Википедии.)
Как клиент узнает, к какому запросу относится ответ?
Что ж, давайте на минуту проигнорируем всю эту задержку в сети и предположим, что конвейерные запросы или ответные сообщения приходят сразу, но только после того, как все они были отправлены.
- Клиент отправляет свои запросы в определенном порядке (без ожидания ответов между запросами).
- Сервер получает запросы в одном и том же порядке (TCP гарантирует, что) одновременно.
- Сервер принимает первое сообщение запроса, обрабатывает его и сохраняет ответ в очереди.
- Сервер принимает второе сообщение запроса, обрабатывает его и сохраняет ответ в очереди.
- (Вы поняли...)
- Сервер отправляет содержимое этой очереди клиенту. Ответы хранятся по порядку, поэтому ответ на первый запрос находится в начале этой очереди, за которым следует ответ на второй запрос и т. Д.
- Клиент получает ответы в том же порядке (TCP гарантирует это) и связывает первый ответ с первым сделанным запросом и так далее.
Это все еще работает, даже если мы не предполагаем, что мы получаем все сообщения сразу, потому что TCP гарантирует, что отправленные данные были получены в том же порядке.
Мы также можем полностью игнорировать сеть и просто просматривать сообщения, которые передаются между сервером и клиентом.
Клиент -> Сервер
GET /request1.html HTTP/1.1
Host: example.com
...
GET /request2.html HTTP/1.1
Host: example.com
...
GET /request3.html HTTP/1.1
Host: example.com
...
Сервер -> Клиент
HTTP/1.1 200 OK
Content-Length: 234
...
HTTP/1.1 200 OK
Content-Length: 123
...
HTTP/1.1 200 OK
Content-Length: 345
...
Самое замечательное в TCP состоит в том, что этот конкретный поток сообщений всегда выглядит одинаково. Вы можете сначала отправить все запросы, а затем получить ответы; вы можете сначала отправить запрос 1, получить первый ответ, отправить оставшиеся запросы и получить оставшиеся ответы; вы можете отправить первый и часть второго запроса, получить часть первого ответа, отправить оставшиеся запросы, получить оставшиеся ответы; и т.д. Поскольку TCP гарантирует сохранение порядка передаваемых сообщений, мы всегда можем связать первый запрос с первым ответом и так далее.
Надеюсь, это ответит на ваш вопрос...