Java socketRead0 Problem

8

Ich entwickle einen Web-Cralwer mit htmlunit und habe alle erforderlichen Timeouts hinzugefügt, aber ich merke, dass die App aufhängt, wenn der Server einer Website gecrawlt wurde, wenn ich JavaVVM verwende, um einen Thread-Dump auszuführen:

%Vor%

Das ist wirklich frustrierend, da ich diese Server nicht kontrollieren kann. Dieses Problem hat schwerwiegende Auswirkungen auf die Leistung meiner Anwendung.

Frage:

  1. Wie kann ich dieses Problem lösen?
  2. Gibt es eine Möglichkeit, eine Liste von Socket-Verbindungen zu erhalten, die von einer Java-Anwendung geöffnet wurden, um damit den Socket zu beenden, wie zum Beispiel, dass der Server die Verbindung geschlossen hat?
John 22.09.2012, 13:31
quelle

3 Antworten

9

Ich glaube, wenn Sie sich in einer nativen Java-Methode befinden, wird die Stack-Ablaufverfolgung RUNNABLE sagen, selbst wenn der Aufruf tatsächlich blockiert ist und auf ein Ereignis wartet. Im Wesentlichen glaube ich nicht, dass Java eine Möglichkeit hat, zu wissen, was eine native Methode eigentlich macht, also markiert sie diese Aufrufe als RUNNABLE. Ich habe das mit socketRead0 () und socketAccept () gesehen - beide blockieren normalerweise.

Sie müssen Ihr Zeitlimit auf eine angemessene Zeitspanne einstellen, so dass Ihre Anfrage eine Zeitüberschreitung hat, wenn der Server nicht antwortet, aber nicht zu kurz, wenn der Server einfach beschäftigt ist. Ihre Anwendung sollte geschrieben werden, um mehrere Threads zu verwenden. Ich würde versuchen, ein Dutzend oder mehr Threads laufen zu lassen und jeden Thread warten auf fünf oder zehn Sekunden für eine Antwort. Es gibt praktisch keinen Overhead, wenn eine Handvoll Threads wartet. Sie sollten auch darauf achten, einen Server mit vielen Anfragen nicht zu bombardieren, wenn Sie einen Webspider schreiben.

    
Geoff 22.09.2012 17:50
quelle
5

Hier ist ein Blog-Eintrag, der möglicherweise verwandt ist: Ссылка

Kurz gesagt, besteht die Lösung darin, sicherzustellen, dass das Socket-Timeout definiert ist. Der Standardwert ist 0, also kein Timeout. Wie genau, das hängt von der Bibliothek ab, in diesem Fall anscheinend com.gargoylesoftware.htmlunit . Auf einen Blick kann die korrekte Methode sein com.gargoylesoftware.htmlunit.WebClient.setTimeout .

    
hyde 25.03.2013 09:59
quelle
1

Wenn sich Ihr Java-Server in Windows befindet, ist Ihr letzter Ausweg SysInternals TCPView.

Ссылка

Hier sehen Sie die Liste aller Prozesse und aller lokalen und entfernten Ports, die Ihre Java-App enthalten. Sie müssen die richtige Verbindung zum Schließen auswählen, und danach wird der Java-Thread eine Ausnahme auslösen und enden.

Natürlich besteht die Gefahr, die falsche Verbindung zu schließen. Schließlich ist diese Methode der letzte Ausweg.

    
sken130 25.03.2014 03:31
quelle

Tags und Links