С чего мне начать расследование SocketTimeoutException: тайм-аут чтения - PullRequest
24 голосов
/ 29 сентября 2011

Время от времени я вижу следующую трассировку стека в журнале, в котором сокет HttpClient истекает при попытке доступа к содержимому text/script с другого сервера. У меня вопрос: какие параметры конфигурации я должен проверить для моего приложения J2EE, работающего в Weblogic, в Linux? Я специально ищу следующее.

  • Параметры тайм-аута JVM
  • HttpClient params
  • Параметры тайм-аута Weblogic или любые другие настройки, например количество потоков и т. Д.
  • J2EE Настройки приложения, такие как конфигурация сервлета и т. Д.
  • Ресурсы операционной системы, такие как потоки, обработчики файлов и процессор
  • Любые другие настройки конфигурации, которые могут повлиять на подключение к сокету
  • Помогут ли дампы потоков?

Вот мой код

HTTPResponse httpClientResponse;
//do some stuff
httpClientResponse.getStatusCode(); // this is where it fails

и это трассировка стека

java.net.SocketTimeoutException: Read timed out
at jrockit.net.SocketNativeIO.readBytesPinned(Native Method)
at jrockit.net.SocketNativeIO.socketRead(SocketNativeIO.java:32)
at java.net.SocketInputStream.socketRead0(SocketInputStream.java)
at java.net.SocketInputStream.read(SocketInputStream.java:129)
at HTTPClient.BufferedInputStream.fillBuff(BufferedInputStream.java:206)
at HTTPClient.BufferedInputStream.read(BufferedInputStream.java:126)
at HTTPClient.StreamDemultiplexor.read(StreamDemultiplexor.java:356)
at HTTPClient.RespInputStream.read(RespInputStream.java:147)
at HTTPClient.RespInputStream.read(RespInputStream.java:108)
at HTTPClient.Response.readResponseHeaders(Response.java:1123)
at HTTPClient.Response.getHeaders(Response.java:846)
at HTTPClient.Response.getStatusCode(Response.java:331)
at HTTPClient.RetryModule.responsePhase1Handler(RetryModule.java:92)
at HTTPClient.HTTPResponse.handleResponseImpl(HTTPResponse.java:872)
at HTTPClient.HTTPResponse.access$000(HTTPResponse.java:62)
at HTTPClient.HTTPResponse$2.run(HTTPResponse.java:839)
at HTTPClient.HTTPResponse$2.run(HTTPResponse.java:837)
at
HTTPClient.HttpClientConfiguration.doAction(HttpClientConfiguration.java:666)
at HTTPClient.HTTPResponse.handleResponse(HTTPResponse.java:837)
at HTTPClient.HTTPResponse.getStatusCode(HTTPResponse.java:242) 

Спасибо

Я буду обновлять мой вопрос, используя НАИМЕНОВАНИЯ ниже.

  1. Для HttpClient не установлен явный тайм-аут, что означает, что http Тайм-аут сеанса сервера может вступать в силу.
  2. SO_TIMEOUT для HttpClient равно 0, что означает, что он должен ждать бесконечно.

Ответы [ 3 ]

16 голосов
/ 30 сентября 2011

Трек 1

Согласно Javadocs Httpclient, похоже, не имеет значения по умолчанию времени ожидания Socket.Чтобы ответить на вопрос в вашем обновлении - тайм-аут сеанса здесь не будет действовать.Значение по умолчанию для Weblogic составляет 30 минут.

Сервер session timeout представляет количество времени, в течение которого HttpSession будет храниться в памяти, если пользователь не обращался к серверу.

время ожидания сокета - это время, в течение которого сокет сервера остается открытым, пока данные передаются обратно вызывающей стороне.Это может быть даже то, что сервер все еще обрабатывает и записывает данные, но это занимает довольно много времени, и клиент только что ожидал его ожидания.

Некоторые ссылки предполагают, что по умолчанию это 60 секунд, но javadocs ничего не говорит,в любом случае вы можете установить это значение примерно на 120 секунд, чтобы посмотреть, поможет ли оно

http://hc.apache.org/httpclient-3.x/apidocs/org/apache/commons/httpclient/params/HttpConnectionParams.html#setSoTimeout(int)

Вам нужно рассчитать время ожидания - если это ясно.Значение - эти ошибки появляются через 30 секунд, 60 секунд или 5 минут после исходящего запроса?

Я бы изменил SO_Timeout и повторил попытку

Трек 2 - параметры ОС

Существуют рекомендуемые параметры BEA для значений NDD, которые определяют, как долговходящие соединения остаются открытыми, сколько в очереди и так далее.В Solaris их можно получить, запустив

/usr/sbin/ndd -get /dev/tcp tcp_time_wait_interval 
/usr/sbin/ndd -get /dev/tcp tcp_conn_req_max_q 
/usr/sbin/ndd -get /dev/tcp tcp_conn_req_max_q0 
/usr/sbin/ndd -get /dev/tcp tcp_ip_abort_interval 
/usr/sbin/ndd -get /dev/tcp tcp_keepalive_interval 

Можете ли вы проверить документы Oracle на наличие эквивалентных команд в Linux и определить, на какие значения они должны быть установлены.На Solaris мой опыт показывает, что по умолчанию недостаточно, и их необходимо повысить до рекомендаций BEA (Oracle)

Трек 3: Журналы Weblogic / External Access

Есть ли у васвключен HTTP Access Logs на сервере?Эти неудавшиеся запросы отображаются с каким-либо размером байта ответа или они показывают 0 размеров ответа?Какой код ошибки или код состояния HTTP возвращается?

Или, возможно, эти тайм-ауты вообще не записываются в журналы доступа?

Здесь я предполагаю внешний сервер, на котором временивыходы происходят также в Weblogic, если нет - этот вопрос направляется команде внешних серверов для их эквивалентной платформы.

** Другое **

Обычно помогают дампы потока, но дампы потока должныбыть взятым на сервер, который имеет проблему тайм-аутаВы являетесь клиентом и успешно установили соединение, после чего оно истекает при чтении ответа.Итак, внешний сервер перегружен?Отсутствие потоков?Процессор высокий?Слишком много одновременных запросов?

0 голосов
/ 15 января 2013

Еще один аспект, который не был рассмотрен здесь, - это брандмауэр.

Я обнаружил, что исключения SocketTimeout часто могут быть связаны с тем, что порт не открыт для связи или брандмауэр блокирует связь только с выбранных компьютеров.

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

Интересные вещи, связанные с проблемами брандмауэра, заключаются в том, что он не дает вам знать, если сервер не работает или не отвечает.Типичное поведение - позволить клиенту ждать вечно.Так что вы всегда оставлены во тьме.Простой telnet на порту сервера должен показать, доступен ли он / открыт для связи.

Надеюсь, это поможет.

0 голосов
/ 29 сентября 2011

Вам следует изучить

(a) установленное по умолчанию или явное HttpClient время ожидания чтения, в зависимости от того, что используется;

(b) почему сервер не отвечает в течение этого периода, если он должен (просмотреть журналы сервера),

(c) в противном случае, почему время ожидания установлено слишком коротким.Многие тайм-ауты установлены слишком короткими, например, несколько секунд.Они должны составлять приличную долю минуты, а если ожидаемое время отклика больше, удвоить или утроить ожидаемое время отклика.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...