【问题标题】:Spring boot: Start an application automatically when Webshere Application Server starts?Spring boot:Websphere Application Server启动时自动启动应用程序?
【发布时间】:2016-09-02 08:57:20
【问题描述】:

假设我有一个 SpringBoot 应用程序作为 WAR 部署到 Websphere Application Server (WAS)。此 WAR 包含一个守护进程,因此它必须在 WAS 启动时立即启动(并且仅启动一次)。

但是,我仍然需要通过 http 请求来激活 SpringBoot Servlet。

现在我明白了 servlet 的概念是作用于 http 请求,我仍然想让它在 appserver 启动时自动启动。这使得我的守护进程可以从独立的 jar/main 移植到 war/webapp。

我尝试了ServletContextListener,但contextInitalized 也只在第一个http 请求时被调用。

我没有 web.xml (servlet 3)。

代码:

@SpringBootApplication
@WebListener
public class DemoApplication extends SpringBootServletInitializer implements ServletContextListener {

    @Override
    public void onStartup(ServletContext servletContext) throws ServletException {
        System.err.println("ONSTARTUP"); 
        super.onStartup(servletContext);
    }

    public static void main(String[] args) {
        SpringApplication.run(DemoApplication.class, args);
    } 

   @Override
   protected SpringApplicationBuilder configure(SpringApplicationBuilder application) {
      return application.sources(DemoApplication.class);
   }


    @Override
    public void contextInitialized(ServletContextEvent sce) {
        System.err.println("contextInitialized"); 
    }

    @Override
    public void contextDestroyed(ServletContextEvent arg0) {
        //
    }
}

和:

@Component
public class DemoRunner implements ApplicationRunner {

    @Override
    public void run(ApplicationArguments arg0) throws Exception {
        System.err.println("I AM RUNNING");
    }

}

当我开始 WAS 时,我第一次明白:

Launching defaultServer (WebSphere Application Server
16.0.0.2/wlp-1.0.13.cl160220160526-2258) on Java HotSpot(TM) 64-Bit Server VM, version 1.7.0_79-b15 (en_US) 
[...]  
[AUDIT   ] CWWKT0016I: Web application available (default_host): http://localhost:9080/demo/ 
[AUDIT   ] CWWKZ0001I: Application test started in 17,282 seconds.

要启动我的 Spring Boot 应用程序,我首先需要访问此链接 (http:/localhost:9080/demo/)。然后它开始滚动,从日志中看到的启动方法开始。但是如何在不发出 http 请求的情况下启动它呢?

[err] ONSTARTUP
  .   ____          _            __ _ _
 /\\ / ___'_ __ _ _(_)_ __  __ _ \ \ \ \
( ( )\___ | '_ | '_| | '_ \/ _` | \ \ \ \
 \\/  ___)| |_)| | | | | || (_| |  ) ) ) )
  '  |____| .__|_| |_|_| |_\__, | / / / /
 =========|_|==============|___/=/_/_/_/
 :: Spring Boot ::        (v1.4.0.RELEASE)
2016-09-02 10:45:52.670  INFO 23716 --- [dPool-thread-48] com.example.DemoApplication              : Starting DemoApplication on [...]
2016-09-02 10:45:58.019  INFO 23716 --- [dPool-thread-48] o.s.c.support.DefaultLifecycleProcessor  : Starting beans in phase 0
[...]
[err] I AM RUNNING
[...]
2016-09-02 10:45:58.093  INFO 23716 --- [dPool-thread-48] com.example.DemoApplication              : Started DemoApplication in 6.372 seconds (JVM running for 31.549)
[...]
[err] contextInitialized
[err] contextInitialized

【问题讨论】:

    标签: spring spring-boot websphere servlet-3.0 servletcontextlistener


    【解决方案1】:

    您可以通过自定义spring dispatch servlet来更改loadOnStartup,这里是示例问题,您可以使用代码

    @Bean
    public static BeanFactoryPostProcessor beanFactoryPostProcessor() {
        return new BeanFactoryPostProcessor() {
    
            @Override
            public void postProcessBeanFactory(
                    ConfigurableListableBeanFactory beanFactory) throws BeansException {
                BeanDefinition bean = beanFactory.getBeanDefinition(
                        DispatcherServletAutoConfiguration.DEFAULT_DISPATCHER_SERVLET_REGISTRATION_BEAN_NAME);
    
                bean.getPropertyValues().add("loadOnStartup", 1);
            }
        };
    }
    

    参考: how to configure 'dispatcherServlet' load on startup by spring boot?

    更新

    好像有一个更简单的方法,你可以在application.properites进行配置

    spring.mvc.servlet.load-on-startup=1

    【讨论】:

    • Spring Boot 现在明确支持这些东西,只需设置spring.mvc.servlet.load-on-startup=1
    • 这 2 个解决方案不起作用。如果我使用上面的配置代码并在返回之前放置一个 println,那么这个 beanFactoryPostProcessor 被调用(所以它被调用),在我发出 HTTP 请求之后,就在启动之后,在 onstartup 之前。
    • @robert for WAS,也许您需要检查 WAS 文档中 server.xml 中的 <webcontainer deferservletload="false"/>
    • @LipingHuang 您可能应该将 deferServletLoad 详细信息添加到答案的顶部,因为这是最相关的配置。
    猜你喜欢
    • 2011-04-06
    • 2018-03-18
    • 2013-12-23
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多