Tomcat 当我们第一次部署WAR文件时,一些代码可以运行吗?

Tomcat 当我们第一次部署WAR文件时,一些代码可以运行吗?,tomcat,web-deployment,Tomcat,Web Deployment,是否有任何方法或API可供我使用,以便在部署新WAR文件时执行部分代码,或者在Tomcat启动时,相应的servlet应连续启动或运行一些代码。您可以在web.xml中包含一个“ContextListener”。当Webb应用程序WAR即将部署/启动时,将创建此类的实例 此代码可以启动一个线程,该线程将一直运行,直到部署应用程序为止 示例:恢复一个旧问题,因为唯一的答案没有显示任何示例 为了在部署/取消部署web应用程序WAR或启动/停止Tomcat时运行自定义代码,您需要: 实现Servlet

是否有任何方法或API可供我使用,以便在部署新WAR文件时执行部分代码,或者在Tomcat启动时,相应的servlet应连续启动或运行一些代码。

您可以在web.xml中包含一个“ContextListener”。当Webb应用程序WAR即将部署/启动时,将创建此类的实例

此代码可以启动一个线程,该线程将一直运行,直到部署应用程序为止


示例:

恢复一个旧问题,因为唯一的答案没有显示任何示例

为了在部署/取消部署web应用程序WAR或启动/停止Tomcat时运行自定义代码,您需要:

  • 实现
    ServletContextListener
    侦听器及其方法
    contextInitialized()
    contextDestroyed()
  • 让Tomcat知道您的实现。根据,您可以将实现类添加到部署描述符,使用
    WebListener
    对其进行注释,或者通过
    ServletContext
    上定义的
    addListener()
    方法之一注册它
  • 以下是一个示例(基于):

    并将以下内容添加到
    web.xml
    (或者,使用
    WebListener
    注释或
    addListener()
    方法):

    
    ...
    com.example.MyServletContextListener
    
    我找到了一种仅在应用程序(*.war)部署时运行某些代码的方法: 它至少适用于jersey servlet和使用javax.ws.rs.core.Application的Javaservlet

    文件ApplicationConfig.java(见下文)中的应用程序包含一个在应用程序部署时调用的方法public getClasses。 因此,在GetClass中添加代码会导致在应用程序部署时执行它。我注意到的唯一一个问题是,奇怪的是,这个函数被调用了两次,不知道为什么,所以我在ApplicationConfig类中添加了一个全局变量,以了解我的代码是否已经运行

    以下是我的解决方案:

    package eu.oca;
    
    import java.util.Set;
    import javax.ws.rs.core.Application;
    
    /**                                                                                                                             
     *                                                                                                                              
     * @author mattei                                                                                                               
     */
    @javax.ws.rs.ApplicationPath("jersey")
    public class ApplicationConfig extends Application {
    
        private boolean alreadyRun = false;
    
        @Override
        public Set<Class<?>> getClasses() {
    
            System.out.println("Sidonie : ApplicationConfig : getClasses : alreadyRun = " + String.valueOf(alreadyRun));
            alreadyRun = true;
            Set<Class<?>> resources = new java.util.HashSet<>();
            addRestResourceClasses(resources);
            return resources;
        }
    
        /**                                                                                                                         
         * Do not modify addRestResourceClasses() method.                                                                           
         * It is automatically populated with                                                                                       
         * all resources defined in the project.                                                                                    
         * If required, comment out calling this method in getClasses().                                                            
         */
        private void addRestResourceClasses(Set<Class<?>> resources) {
            resources.add(eu.oca.ResultatGeneralAF.class);
            resources.add(eu.oca.ResultatGeneralF.class);
            resources.add(eu.oca.ResultatMesuresAF.class);
            resources.add(eu.oca.ResultatMesuresF.class);
            resources.add(eu.oca.SidonieAccueilD.class);
            resources.add(eu.oca.SidonieWelcomeR.class);
        }
    
    }
    
    包eu.oca;
    导入java.util.Set;
    导入javax.ws.rs.core.Application;
    /**                                                                                                                             
    *                                                                                                                              
    *@作者马泰
    */
    @javax.ws.rs.ApplicationPath(“jersey”)
    公共类应用程序配置扩展应用程序{
    私有布尔值alreadyRun=false;
    @凌驾
    public Set>resources=new java.util.HashSet();
    添加资源类(资源);
    归还资源;
    }
    /**                                                                                                                         
    *不要修改addRestResourceClasses()方法。
    *它会自动填充
    *项目中定义的所有资源。
    *如果需要,在getClasses()中调用此方法时注释掉。
    */
    
    私有void addrestresourcelasses(那么,如果我需要该程序持续运行,那么我该怎么办?你可以使用System.exec启动一个进程。即使应用程序未部署或容器停止,该进程也会继续运行。先生,我需要在部署后运行一个可以在后台持续运行的servlet。我该如何做?有什么建议吗?实现上下文Listener接口,并在“contextInitialized”方法中启动一个守护进程线程。这将使您的代码在后台连续运行。
    <web-app id="WebApp_ID" version="2.4" xmlns="http://java.sun.com/xml/ns/j2ee" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://java.sun.com/xml/ns/j2ee http://java.sun.com/xml/ns/j2ee/web-app_2_4.xsd">
        ...
        <listener>
            <listener-class>com.example.MyServletContextListener</listener-class>
        </listener>
    </web-app>
    
    package eu.oca;
    
    import java.util.Set;
    import javax.ws.rs.core.Application;
    
    /**                                                                                                                             
     *                                                                                                                              
     * @author mattei                                                                                                               
     */
    @javax.ws.rs.ApplicationPath("jersey")
    public class ApplicationConfig extends Application {
    
        private boolean alreadyRun = false;
    
        @Override
        public Set<Class<?>> getClasses() {
    
            System.out.println("Sidonie : ApplicationConfig : getClasses : alreadyRun = " + String.valueOf(alreadyRun));
            alreadyRun = true;
            Set<Class<?>> resources = new java.util.HashSet<>();
            addRestResourceClasses(resources);
            return resources;
        }
    
        /**                                                                                                                         
         * Do not modify addRestResourceClasses() method.                                                                           
         * It is automatically populated with                                                                                       
         * all resources defined in the project.                                                                                    
         * If required, comment out calling this method in getClasses().                                                            
         */
        private void addRestResourceClasses(Set<Class<?>> resources) {
            resources.add(eu.oca.ResultatGeneralAF.class);
            resources.add(eu.oca.ResultatGeneralF.class);
            resources.add(eu.oca.ResultatMesuresAF.class);
            resources.add(eu.oca.ResultatMesuresF.class);
            resources.add(eu.oca.SidonieAccueilD.class);
            resources.add(eu.oca.SidonieWelcomeR.class);
        }
    
    }