Wie implementiert man einen Thread-Pool, der am Ende der Ausführung automatisch heruntergefahren wird?
-
16-10-2019 - |
Frage
Ich schreibe einen Java-Client, der theoretisch in einer anderen Umgebung verwendet werden könnte:Java main(), in einem Servlet-Container oder per Abhängigkeitsinjektion.
Der Client implementiert internes Verbindungs-Thread-Pooling.
Das Problem bei diesem Ansatz besteht darin, dass Benutzer des Clients, die nicht wissen, dass ein interner Thread-Pool implementiert ist, feststellen, dass ihre Anwendung beim Herunterfahren „hängt“.Meine Benutzer müssen wissen, dass sie eine Shutdown()-Nachricht an die Bibliothek senden müssen.
Ich frage mich, ob es einen anderen alternativen Ansatz geben könnte, der es mir einerseits ermöglichen würde, einen Thread-Pool für meine Verbindungen zu erstellen;und andererseits ein Ereignis abfangen, vielleicht ein JVM-Ereignis, das anzeigt, dass die JVM ausfällt, was es mir ermöglicht, meine Shutdown()-Implementierung aufzurufen.
Lösung
Obwohl Sie Hooks hinzufügen können, wie zuvor vorgeschlagen, besteht das Problem wahrscheinlich immer noch darin, dass der Thread-Pool immer noch über aktive Threads verfügt.
Ich glaube, wenn Sie Ihre einzelnen Threads als „Daemons“ markieren (über die Thread.setDaemon-Methode), bleibt die JVM nicht am Leben, wenn nur noch Daemon-Threads übrig sind.
Aus dem JavaDoc:
Markiert diesen Thread entweder als Daemon-Thread oder als Benutzer-Thread.Die Java Virtual Machine wird beendet, wenn die einzigen laufenden Threads alle Daemon-Threads sind.
Wenn auf diese Weise Ihr primärer Nicht-Daemon-Thread beendet wird, bleibt die JVM nicht hängen, weil der andere Thread ausgeführt wird, und dies löst Ihre Shutdown-Hooks aus, ohne dass explizit Beendigungsanweisungen an die verschiedenen Threads gesendet werden müssen.
Andere Tipps
Runtime.getRuntime().addShutdownHook()
wäre das, woran ich denken würde. http://blog.yohanliyanage.com/2010/10/know-the-jvm-2-shutdown-hooks/ hat eine gute Erklärung.Hilft das?
Wenn das Problem darin besteht, dass Benutzer Ihres Codes nicht wissen, dass ein Thread-Pool heruntergefahren werden muss, besteht die Lösung vielleicht darin, sie darauf aufmerksam zu machen?In der Factory-Methode oder im Konstruktor für die entsprechende Klasse müssen Sie Folgendes haben: ExecutorService
als Argument zu verwenden, daher ist der Aufrufer für seinen Lebenszyklus verantwortlich.Das heißt, Sie nutzen die Abhängigkeitsinjektion, um die Politik nach oben zu treiben.