У нас есть набор серверов, настроенных для использования нашего нового блестящего API, который заменит наш старый API, написанный на загадочном языке.
Новое приложение представляет собой кластер серверов, использующих узел, сразу за NGINX.
Это кластер того же типа, что и для старого API.
Есть еще один сервер, сидящий за этими двумя кластерами, использующий NGINX для маршрутизации трафика к одному или другому.
Прямо сейчас новый кластер получает намного меньше 1% трафика, тогда как старый кластер получает гораздо больше, чем 99% трафика.
Журналы показывают, что клиент (клиент, сидящий перед маршрутизатором NGINX) всегда своевременно получает ответы (независимо от того, какой кластер обрабатывает запрос)
Журналы также показывают, что узел своевременно отвечает на свой локальный NGINX.
Старый NGINX / API работает хорошо.
Однако ЛОКАЛЬНЫЕ NGINX для кластера узлов регистрируют, что для каждого запроса требуется время, необходимое узлу для ответа ... плюс дополнительные 5 секунд.
Небольшое исследование доказывает, что это связано с параметром конфигурации lingering_close ..., который установлен на 5 секунд. Согласно документации, задержка закрытия использует «эвристику», чтобы решить, когда оставаться открытым.
http://nginx.org/en/docs/http/ngx_http_core_module.html#lingering_close
Это более чем расплывчато.
Мы знаем, что соединение остается открытым только в течение 5 секунд, когда ответы меньше 1,1k. Я знаю, что это странно ... но "эвристика"
Если мы отключим lingering_close ... соединения закрываются без воздействия эвристики.
Похоже, этого никогда не происходит на СТАРОМ кластере.
Есть ли у кого-нибудь более четкая информация о том, какая эвристика может поддерживать соединение, и, возможно, некоторые советы о том, как действовать.
Меня больше всего беспокоит то, что весь трафик перемещается во второй кластер, и все эти открытые соединения начинают вызывать проблемы с производительностью.
Все дело в индикации того, что в сокете может остаться больше данных. Например. задержка закрытия включена, если во время обработки было прочитано не полное тело запроса, или если в буфере остались еще данные, или если сокет находится в активном состоянии.
Возможно, вас заинтересует это изменение, которое значительно снижает вероятность завершения работы в Linux: http://hg.nginx.org/nginx/rev/f7849bfb6d21