Re: proxy http version 2; без SSL, для мультиплексирование запросов к бекенду

S.A.N nginx-forum на forum.nginx.org
Вт Май 24 14:38:46 UTC 2016


> > Nginx никогда не посылает запрос в то же соединение, пока не
> получит
> > ответ
> > и соединение освободиться.  Т.н. pipelining он не умеет и не
> > использует.
> > 
> > Если бы следующий запрос пришел до того, как на первый был получен
> > ответ,
> > то он бы был отправлен на бекенд в другом соединении.
> > 
> > Т.е. никакой проблемы между nginx и бекендом нет.
> 
> Да, конечно Nginx не пошлет второй и третий запрос на бекенд, пока
> первый не ответит, в этом и проблема, потому что он ждет ответа на
> первый запрос, я бы ещё понял если бы Nginx не ждал ответа на первый
> запрос и отправил второй и третий запрос в другом свободном конекте
> или открыл новый конект, но Nginx эти запросы будет держать в очереди
> и это очень плохо.
> Могу выслать код теста.
> 

Я ещё раз проверил, Nginx разносит три запроса из одного клиенского
соеденения, по разным соединениям бекенда только если клиент сделал запросы
по протоколу HTTP/2, если клиент сделает эти три запроса по протоколу
HTTP/1.1, тогда Nginx никогда не разносит запросы из одного клиентского
соединения по разным соединениям бекенда.

Проверил на Nginx/1.9.15 без стороних модулей.
Я здесь выложу исходники тест скриптов, они не большие и результат, я
тестировал в nc чтобы убедится что все три запроса отправляются в одном
соединение.

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

Три РНР скрипта:

-------------------------------------------------- 1.php
--------------------------------------------------
<?php

sleep(3);

header('X-Time: '.time());
header('Content-Length: 3');

echo "1\n\n";


-------------------------------------------------- 2.php
--------------------------------------------------
<?php

sleep(2);

header('X-Time: '.time());
header('Content-Length: 3');

echo "2\n\n";

-------------------------------------------------- 3.php
--------------------------------------------------
<?php

sleep(1);

header('X-Time: '.time());
header('Content-Length: 3');

echo "3\n\n";


-------------------------------------------------- console# nc 127.0.0.1 80
--------------------------------------------------
GET /test/1.php HTTP/1.1
Host: localhost

GET /test/2.php HTTP/1.1
Host: localhost

GET /test/3.php HTTP/1.1
Host: localhost

HTTP/1.1 200 OK
Server: nginx/1.9.15
Date: Tue, 24 May 2016 14:22:19 GMT
Content-Type: text/html; charset=UTF-8
Content-Length: 3
Connection: keep-alive
X-Powered-By: PHP/7.0.6
X-Time: 1464099738

1

HTTP/1.1 200 OK
Server: nginx/1.9.15
Date: Tue, 24 May 2016 14:22:21 GMT
Content-Type: text/html; charset=UTF-8
Content-Length: 3
Connection: keep-alive
X-Powered-By: PHP/7.0.6
X-Time: 1464099741

2

HTTP/1.1 200 OK
Server: nginx/1.9.15
Date: Tue, 24 May 2016 14:22:22 GMT
Content-Type: text/html; charset=UTF-8
Content-Length: 3
Connection: keep-alive
X-Powered-By: PHP/7.0.6
X-Time: 1464099743

3

-------------------------------------------------- 

Посмотрите на заголовки X-Time, видно что скрипты выполнялись
последовательно, вначале первый потом второй потом третий.
Если бы Nginx эти три запроса распределил на три разных соединения с
бекендом, в заголовках X-Time было бы время в обратном порядке, потому что в
скриптах вызывается sleep со значением 3s - 2s - 1s соответственно.

Posted at Nginx Forum: https://forum.nginx.org/read.php?21,266693,267096#msg-267096



Подробная информация о списке рассылки nginx-ru