apache2 игнорирует MaxKeepAliveRequests, произвольно закрывает соединения

У нас есть внешний сервер Tomcat, который проксирует наш сервер приложений Apache 2.2.11 и работает на 64-битном экземпляре Fedora 2.6.21.7 EC2 2xlarge (AKI aki-b51cf9dc). Apache работает с mod_perl и не имеет потоков.

Мы пытаемся, чтобы соединения долгое время сохранялись между Tomcat, работающим на другом экземпляре EC2, и сервером Apache, но не сохраняли соединения от внешних клиентов, поступающих непосредственно на сервер Apache. Наш конфиг выглядит так:

Listen 80
NameVirtualHost *:80

# used for external clients
<VirtualHost *:80>
    ServerName xxx.yyy.com
    ServerAlias *.yyy.com
    DocumentRoot "/var/www/html"
    KeepAlive Off
</VirtualHost>

# used from tomcat server on local network
<VirtualHost *:80>
    ServerName ip-<Apache-server-local-IP>.ec2.internal
    KeepAlive On
    KeepAliveTimeout 3600
    MaxKeepAliveRequests 0
    DocumentRoot "/var/www/html"
</VirtualHost>

TimeOut 60
MinSpareServers 20
MaxSpareServers 30
StartServers 20
MaxClients 60
GracefulShutdownTimeout 90

Мы перепробовали все виды значений для MaxKeepAliveRequests и KeepAliveTimeout, и сервер определенно некоторое время поддерживает соединение с Tomcat, но всегда закрывает его в течение нескольких секунд, когда обрабатывается только несколько десятков запросов. Возможно, важно то, что я никогда не видел, чтобы процесс поддерживал 100 или более соединений в сокете, наблюдая за использованием mod_status.

Постоянных соединений с клиентами, не являющимися Tomcat, никогда не бывает, поэтому мы знаем, что здесь есть некоторая разница, и конфигурация VirtualHost определенно применяется в обоих случаях.

Я должен отметить, что все запросы от Tomcat - это POST, а остальные представляют собой смесь POST и GET.

Когда я просматриваю трафик на заданном порту с помощью tcpdump, я ясно вижу, как правильно обрабатывается количество проверок POST, а затем в какой-то момент после получения хорошего ответа (200, данные выглядят нормально) сервер Apache немедленно закрывает соединение, отправляя FIN к Tomcat. Это происходит в тех случаях, когда нет абсолютно никакой разницы между последним и предпоследним запросами или ответами, кроме второстепенных данных, таких как IP-адрес реального клиента, поэтому при обработке запроса нет никаких указаний на перебои в работе сервера. И, конечно, в журналах ошибок нет ничего подозрительного, и сами процессы httpd не умирают.

Из netstat мы видим, что соединения с сервером Tomcat остаются открытыми в течение нескольких секунд, но довольно быстро переключаются между диапазонами удаленных портов, проверяя то, что мы видим в другом месте. Это похоже на то, как будто Apache пытается справедливо распределить соединения, чтобы не дать постоянным изголодаться по остальным - но этого не произойдет, не так ли?!

Мне бы не хотелось, чтобы мне сказали, что мы делаем что-то немое! Пожалуйста, пожалуйста, скажи мне, что я идиот или, по крайней мере, близорукий...

2 ответа

Какова стоимость cat /proc/sys/net/ipv4/tcp_keepalive_time на Tomcat?

Это необычно низко? По умолчанию 7200 (то есть 2 часа)

MaxKeepAliveRequests должен быть равен -1, а не нулю на ec2.internal

Другие вопросы по тегам