2

Мы запускаем приложение в Amazon Elastic Beanstalk, используя их 64-битный контейнер Python. Это приложение порождает потоки, позволяет им жить в течение определенного времени, а затем закрывает их перед повторением по одному и тому же шаблону в течение произвольного периода времени.Темы оставляют открытые файлы для запросов TCP для услуг Amazon

Каждый из этих потоков создает несколько файлов в системе Unix - файл журнала, созданный с использованием модуля протоколирования с FileHandler, а также различные подключения к SQS, EC2, Cloudwatch, Autoscale и S3 - все это делается с помощью модуля boto. Эти соединения создают TCP-файлы, которые могут быть идентифицированы в результатах:

lsof -p {process-id} 

Когда нить заканчивается, мы удаляем FileHandler и закройте регистратор. Мы также явно закрываем каждое соединение, которое было создано с помощью boto. В любых случаях, когда это возможно, мы создаем соединения или файлы, используя синтаксис with, чтобы впоследствии можно было утилизировать любые ресурсы (надеюсь).

Однако то, что мы обнаруживаем, заключается в том, что после того, как потоки были завершены, в состоянии CLOSE_WAIT есть TCP-запросы, все еще сохраняющиеся в виде открытых файлов в системе. Это не сразу проблема, но в конечном итоге количество открытых файлов в системе превышает ограничение, установленное в /etc/security/limits.conf, и скрипт Python прекращает выполнение в результате этого.

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

Есть шаблон, который отсутствует здесь вне предложенных вариантов close() соединение?

+0

'CLOSE_WAIT' может указывать, что куча данных была« отправлена ​​»на удаленную сторону, но она еще не получена (ACKed). Каково приблизительное временное окно, когда сокеты открыты до исчерпания количества открытых файлов? И сколько данных передается? –

+0

Розетки открыты более полутора часов, по крайней мере, с последними испытаниями, которые мы проводили на нем. Я могу повторить это сейчас, чтобы проверить. Данные, передаваемые каждым потоком, минимальны - чтение примерно 100 сообщений <5 КБ SQS и загрузка 150 текстовых текстовых файлов на S3 при завершении потока суммируют его. –

+0

Тогда как насчет протокола? Удаленная сторона ожидает больше данных? –

ответ

0

Я обнаружил ту же проблему с розетками в состоянии CLOSE_WAIT с boto 2.3.0. Причина заключается в том, что соединение устанавливается следующим образом:

import boto.ec2 
conn = boto.ec2.connect_to_region("eu-west-1") 

Это в первую открыть соединение, чтобы найти все регионы, а затем откройте второе соединение данного региона. Но первая связь никогда не закрывалась. Можно установить соединение ec2 вручную через boto.connect_ec2_endpoint(...) или использовать boto >= 2.7.0 , где используется статический список областей.