Java.net.SocketException: программное обеспечение вызвало прерывание соединения: recv failed

Я не смог найти адекватного ответа на то, что означает следующая ошибка:

java.net.SocketException: Software caused connection abort: recv failed

Примечания:

  • Эта ошибка нечастая и непредсказуемая; хотя получение этой ошибки означает, что все будущие запросы на URI также потерпят неудачу.
  • Единственное решение, которое работает (также, только изредка), - перезагрузить Tomcat и/или фактический компьютер (в этом случае Windows).
  • URI определенно доступен (как подтверждается, попросив браузер сделать выборку).

Соответствующий код:

BufferedReader reader;
try { 
 URL url = new URL(URI);
 reader = new BufferedReader(new InputStreamReader(url.openStream())));
} catch( MalformedURLException e ) { 
 throw new IOException("Expecting a well-formed URL: " + e); 
}//end try: Have a stream

String buffer;
StringBuilder result = new StringBuilder();
while( null != (buffer = reader.readLine()) ) { 
 result.append(buffer); 
}//end while: Got the contents.
reader.close();

Ответ 1

Это обычно означает, что произошла сетевая ошибка, такая как таймаут TCP. Я бы начал с размещения сниффера (wirehark) в соединении, чтобы увидеть, есть ли у вас какие-либо проблемы. Если есть ошибка TCP, вы должны уметь это видеть. Кроме того, вы можете проверить свои журналы маршрутизатора, если это применимо. Если беспроводная связь задействована в любом месте, это еще один источник таких ошибок.

Ответ 2

Это также происходит, если ваш клиент TLS не может быть аутентифицирован сервером, настроенным на необходимость аутентификации клиента.

Ответ 3

Единственный раз, когда я видел что-то подобное, случается, когда у меня плохое соединение или когда кто-то закрывает сокет, который я использую из другого контекста потока.

Ответ 4

Эта ошибка возникает, когда соединение закрывается внезапно (когда TCP-соединение reset, в то время как все еще есть данные в буфере отправки). Условие очень похоже на гораздо более распространенное "Connection reset by peer". Это может произойти спорадически при подключении через Интернет, но также систематически, если выбор времени правилен (например, с помощью соединений keep-alive на локальном хосте).

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

Не используйте URL.open(), используйте Apache-Commons HttpClient, в котором есть механизм повтора, объединение пулов, сохранение и многие другие особенности.

Использование образца:

HttpClient httpClient = HttpClients.custom()
            .setConnectionTimeToLive(20, TimeUnit.SECONDS)
            .setMaxConnTotal(400).setMaxConnPerRoute(400)
            .setDefaultRequestConfig(RequestConfig.custom()
                    .setSocketTimeout(30000).setConnectTimeout(5000).build())
            .setRetryHandler(new DefaultHttpRequestRetryHandler(5, true))
            .build();
// the httpClient should be re-used because it is pooled and thread-safe.

HttpGet request = new HttpGet(uri);
HttpResponse response = httpClient.execute(request);
reader = new BufferedReader(new InputStreamReader(response.getEntity().getContent()));
// handle response ...

Ответ 5

Получаете ли вы доступ к данным HTTP? Можете ли вы использовать библиотеку HttpClient вместо стандартной библиотеки? Библиотека имеет больше опций и обеспечит лучшие сообщения об ошибках.

http://hc.apache.org/httpclient-3.x/

Ответ 6

Попробуйте добавить 'autoReconnect = true' в строку подключения jdbc

Ответ 7

Это будет происходить время от времени либо в случае сбоя соединения, либо когда удаленный хост завершает свое соединение (закрытое приложение, выключение компьютера и т.д.). Вы можете избежать этого, самостоятельно управляя сокетами и обрабатывая отключения в своем приложении через свой протокол связи, а затем вызываете shutdownInput и shutdownOutput, чтобы очистить сеанс.

Ответ 8

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

Ответ 9

Если вы используете Netbeans для управления Tomcat, попробуйте отключить HTTP-монитор в Tools-Servers

Ответ 10

У меня тоже была эта проблема. Мое решение было:

sc.setSoLinger(true, 10);

КОПИРОВАНИЕ ИЗ ВЕБ-САЙТА → Используя метод setSoLinger(), вы можете явно установить задержку перед отправкой reset, предоставляя больше времени для чтения или отправки данных.

Возможно, это не ответ для всех, но для некоторых людей.