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

Обратные прокси-серверы HTTP обычно включают HTTP Keep-Alive на стороне клиента прокси-соединения, а не на стороне сервера?

HAProxy имеет возможность включить HTTP keep-alive на стороне клиента (client <-> HAProxy), но отключить его на стороне сервера (HAProxy <-> server).

Некоторые из наших клиентов подключаются к нашему веб-сервису через спутник, поэтому задержка составляет ~ 600 мс, и я думаю, что включение keep-alive немного ускорит процесс. Я прав?

Поддерживается ли это Nginx? Широко ли реализована эта функция в других программных и аппаратных балансировщиках нагрузки? Что еще кроме HAProxy?

редактировать: Мой ответ охватывает только исходный неотредактированный вопрос: типичны ли подобные вещи для балансировщиков нагрузки / обратных прокси. Я не уверен, поддерживает ли это nginx / product X, 99,9% моего опыта обратного проксирования связаны с HAproxy.

Верный. HTTP Keep-Alive на стороне клиента, но не на стороне сервера.

Зачем?

Если вы разберете несколько деталей, вы сможете быстро понять, почему это преимущество. В этом примере представим, что мы загружаем страницу www.example.com, и эта страница включает 3 изображения, img [1-3] .jpg.

Браузер загружает страницу без Keep-Alive

  1. Клиент устанавливает TCP-соединение с www.example.com через порт 80
  2. Клиент выполняет HTTP-запрос GET для "/"
  3. Сервер отправляет HTML-контент URI "/" (который включает HTML-теги, ссылающиеся на 3 изображения)
  4. Сервер закрывает TCP-соединение
  5. Клиент устанавливает TCP-соединение с www.example.com через порт 80
  6. Клиент выполняет HTTP-запрос GET для "/img1.jpg"
  7. Сервер отправляет изображение
  8. Сервер закрывает TCP-соединение
  9. Клиент устанавливает TCP-соединение с www.example.com через порт 80
  10. Клиент выполняет HTTP-запрос GET для "/img2.jpg"
  11. Сервер отправляет изображение
  12. Сервер закрывает TCP-соединение
  13. Клиент устанавливает TCP-соединение с www.example.com через порт 80
  14. Клиент выполняет HTTP-запрос GET для "/img3.jpg"
  15. Сервер отправляет изображение
  16. Сервер закрывает TCP-соединение

Обратите внимание на то, что были установлены и закрыты 4 отдельных сеанса TCP.

Браузер загружает страницу с Keep-Alive

HTTP Keep-Alive позволяет одному TCP-соединению обслуживать несколько HTTP-запросов, один за другим.

  1. Клиент устанавливает TCP-соединение с www.example.com через порт 80
  2. Клиент выполняет HTTP-запрос GET для «/», а также просит сервер сделать это HTTP-сеансом Keep-Alive.
  3. Сервер отправляет HTML-содержимое URI "/" (который включает HTML-теги, ссылающиеся на 3 изображения)
  4. Сервер не закрывается TCP-соединение
  5. Клиент выполняет и HTTP-запрос GET для "/img1.jpg"
  6. Сервер отправляет изображение
  7. Клиент выполняет и HTTP-запрос GET для "/img2.jpg"
  8. Сервер отправляет изображение
  9. Клиент выполняет и HTTP-запрос GET для "/img3.jpg"
  10. Сервер отправляет изображение
  11. Сервер закрывает TCP-соединение, если в течение периода ожидания HTTP Keep-Alive больше не поступают HTTP-запросы.

Обратите внимание, что с Keep-Alive устанавливается и закрывается только 1 TCP-соединение.

Почему Keep-Alive лучше?

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

  1. Клиент отправляет пакет SYN (chronise)
  2. Сервер отправляет обратно SYN (chronise) ACK (подтверждение), SYN-ACK
  3. Клиент отправляет пакет ACK (подтверждение)
  4. TCP-соединение теперь считается активным как для клиента, так и для сервера.

В сетях существует задержка, поэтому каждый шаг в трехстороннем рукопожатии занимает определенное время. Допустим, между клиентом и сервером есть 30 мсек. Посылка IP-пакетов туда и обратно, необходимая для установления TCP-соединения, означает, что для установления TCP-соединения требуется 3 x 30 мс = 90 мс.

Это может показаться не таким уж большим, но если учесть, что в нашем исходном примере мы должны установить 4 отдельных TCP-соединения, это составит 360 мс. Что, если задержка между клиентом и сервером составляет 100 мс вместо 30 мс? Затем для установления наших 4 соединений требуется 1200 мс.

Что еще хуже, для загрузки типичной веб-страницы может потребоваться гораздо больше, чем просто 3 изображения, может быть несколько файлов CSS, JavaScript, изображений или других файлов, которые клиент должен запросить. Если страница загружает 30 других файлов, а задержка клиент-сервер составляет 100 мс, сколько времени мы потратим на установление TCP-соединений?

  1. Чтобы установить 1 TCP-соединение, требуется трехкратная задержка, т.е. 3 x 100 мс = 300 мс.
  2. Мы должны сделать это 31 раз, один раз для страницы и еще 30 раз для каждого другого файла, на который ссылается страница. 31 x 300 мс = 9,3 секунды.

9,3 секунды потрачено на установление TCP-соединений для загрузки веб-страницы, которая ссылается на 30 других файлов. И это даже не считая времени, потраченного на отправку HTTP-запросов и получение ответов.

С HTTP Keep-Alive нам нужно установить только 1 TCP-соединение, что занимает 300 мс.

Если HTTP Keep-Alive настолько хорош, почему бы не использовать его и на стороне сервера?

Обратные прокси-серверы HTTP (например, HAproxy) обычно развертываются очень близко к внутренним серверам, для которых они проксируются. В большинстве случаев задержка между обратным прокси-сервером и его внутренними серверами будет менее 1 мс, поэтому установление TCP-соединения происходит намного быстрее, чем между клиентом.

Но это только половина причины. HTTP-сервер выделяет определенный объем памяти для каждого клиентского соединения. С Keep-Alive он будет поддерживать соединение, и, как следствие, он будет поддерживать определенный объем памяти, используемый на сервере, до тех пор, пока не будет достигнут тайм-аут Keep-Alive, который может составлять до 15 секунд, в зависимости от конфигурации сервера. .

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

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

Nginx поддерживает keep-alive с обеих сторон.