web-dev-qa-db-fra.com

Thread d'arrière-plan pour une application de servlet Tomcat

Je ne suis pas très familier avec Tomcat, dans ma tête, il est essentiellement résumé comme un serveur cgi qui enregistre la JVM entre les appels - je sais qu'il peut faire beaucoup plus que cela, cependant.

Je cherche un moyen de lancer un thread en arrière-plan lors du démarrage d'un serveur Tomcat, qui mettrait régulièrement à jour le contexte du serveur (dans mon cas particulier, c'est un thread qui écoute les battements de cœur de certains autres services et mises à jour informations de disponibilité, mais on peut imaginer une variété d'utilisations pour cela).

Existe-t-il un moyen standard de procéder? Le lancement et la mise à jour/interrogation du contexte?

Tout pointeur vers la documentation pertinente et/ou des exemples de code serait très apprécié.

60
SquareCog

Si vous souhaitez démarrer un thread lorsque votre WAR est déployé, vous pouvez définir un écouteur de contexte dans le web.xml:

<web-app>
    <listener>
       <listener-class>com.mypackage.MyServletContextListener</listener-class>
    </listener>
</web-app>

Ensuite, implémentez cette classe quelque chose comme:

public class MyServletContextListener implements ServletContextListener {

    private MyThreadClass myThread = null;

    public void contextInitialized(ServletContextEvent sce) {
        if ((myThread == null) || (!myThread.isAlive())) {
            myThread = new MyThreadClass();
            myThread.start();
        }
    }

    public void contextDestroyed(ServletContextEvent sce){
        try {
            myThread.doShutdown();
            myThread.interrupt();
        } catch (Exception ex) {
        }
    }
}
79
Chris Thornhill

Je cherche un moyen de lancer un thread d'arrière-plan lorsqu'un serveur Tomcat démarre

Je pense que vous cherchez un moyen de lancer un thread d'arrière-plan lorsque votre application Web est lancée par Tomcat.

Cela peut être fait en utilisant un ServletContextListener . Il est enregistré dans web.xml et sera appelé au démarrage ou à l'arrêt de votre application. Vous pouvez ensuite créer (et arrêter plus tard) votre Thread, en utilisant les méthodes normales Java pour créer un Thread (ou ExecutionService).

12
Thilo

Mettre <load-on-startup>1</load-on-startup> Dans le bloc <servlet> Dans votre web.xml forcera la init() de votre servlet à se produire dès le démarrage de Tomcat, plutôt que d'attendre la première demande. . Ceci est utile si vous souhaitez générer le thread d'arrière-plan à partir de init().

5
divbyzero

Si vous utilisez un framework à ressort, vous pouvez également spécifier la classe/thread que vous souhaitez initialiser dans le beans.xml. Ainsi, au démarrage de Tomcat, beans.xml initialisera toutes les classes qui y sont mentionnées. Vous pouvez également passer des arguments de constructeur si nécessaire. Voici l'exemple de la même chose.

beans.xml

<bean id="monitoringSvc" class="com.mypackage.MonitoringService">
    <constructor-arg value="60"></constructor-arg>
</bean>

MonitoringService.Java

public class MonitoringService{

     private MyThread myThread;

     public MonitoringService(int seconds){
          myThread = new MyThread(seconds);
          myThread.start();
     }
}    
2
Akshay

Je voudrais juste apporter un petit changement à la réponse très détaillée que Chris a donnée; Je définirais myThread pour être un thread Daemon par myThread.setDaemon(true); qui gardera fondamentalement le thread actif tant que vous aurez d'autres threads non-Daemon qui ont besoin de votre thread d'arrière-plan. Une fois tous ces threads terminés, votre thread Daemon est arrêté par la JVM et vous n'avez pas besoin de le gérer vous-même dans contextDestroyed. Mais c'est juste mes 2 cents.

2
Ittai