2015-01-30 3 views
12

스프링 부트 애플리케이션에서 (기본 Tomcat) 웹 서버가 완전히 초기화되고 트래픽을 취할 준비가 될 때까지 기다렸다가 HTTP 요청을 보내라는 메시지를 다른 응용 프로그램에 보내기 전에 기다려야합니다 나에게 (내 /health 히트 특히 모니터링 시스템).스프링 부트 - 웹 서버가 시작될 때까지 기다리십시오.

나는 다른 응용 프로그램에 메시지를 보내는 논리를 ApplicationListener<ContextRefreshedEvent>에 넣으려고했지만 아직 너무 빠릅니다. 다른 응용 프로그램은 나에게 요청을 보내고 실패합니다. 지금은 onApplicationEvent에 지연을 넣었습니다.하지만 작동하지만 해키하고 열정이 있습니다.

나는 또한 ServletContextInitializer을 추가하려고했지만 그보다 더 일찍 해고했습니다.

Tomcat API를 사용해야한다고 가정하고 있지만 Boot API에이 API가 있는지 확인하고 싶습니다.

+0

에 다음 속성을 추가 특정 프로파일에서 실행이 청취자를 필요 : //stackoverflow.com/a/4747639/283084? 또한 LB 뒤에 앱을 숨길 수 있으며'/ health'에 대한 요청이 HTTP OK (200)를 반환 할 때까지 LB는 앱을 풀로 가져 가지 않습니다. – harpun

답변

16

가장 간단한 방법은 SpringApplication.run()이 반환 된 후 메시지를 보내는 것입니다. Tomcat (또는 지원되는 다른 내장 된 컨테이너)이 완전히 시작되고 구성된 포트에서 수신 대기해야만이 메소드가 리턴됩니다. 그러나 이것은 간단하지만 기본 구성 클래스와 응용 프로그램의 런타임 논리 중 일부와 관련된 문제가 혼합되어있어 매우 깔끔한 방법은 아닙니다.

대신 SpringApplicationRunListener을 사용할 수 있습니다. finished()은 Tomcat이 완전히 시작되고 구성된 포트에서 수신 대기 할 때까지 호출되지 않습니다.

실행 수신기를 나열하는 src/main/resources/META-INF/spring.factories 파일을 만듭니다. 예 :

org.springframework.boot.SpringApplicationRunListener=com.example.MyRunListener 

필요한 생성자를 사용하여 실행 수신기를 만들고 SpringApplicationRunListener을 구현합니다. 예를 들어 : 허용 대답에 언급 한 바와 같이

public class MyApplicationListener implements ApplicationListener<ApplicationReadyEvent>, Ordered { 

    @Override 
    public void onApplicationEvent(ApplicationReadyEvent event) { 
     //do stuff now that application is ready 
    } 

    @Override 
    public int getOrder() { 
     return Ordered.LOWEST_PRECEDENCE; 
    } 
} 

또한, 당신은을 만들 수 있습니다

package com.example; 

import org.springframework.boot.SpringApplication; 
import org.springframework.boot.SpringApplicationRunListener; 
import org.springframework.context.ConfigurableApplicationContext; 
import org.springframework.core.env.ConfigurableEnvironment; 

public class MyRunListener implements SpringApplicationRunListener { 

    public MyRunListener(SpringApplication application, String[] args) { } 

    @Override 
    public void started() { } 

    @Override 
    public void environmentPrepared(ConfigurableEnvironment environment) { } 

    @Override 
    public void contextPrepared(ConfigurableApplicationContext context) { } 

    @Override 
    public void contextLoaded(ConfigurableApplicationContext context) { } 

    @Override 
    public void finished(ConfigurableApplicationContext context, Throwable exception) { 
     // Send message; Tomcat is running and listening on the configured port(s) 
    } 
} 
+1

위대한 작품. 관심있는 빈을 구현할 수있는 또 다른 인터페이스를 만들었고, 내 'SpringApplicationRunListener'가 그들을 컨텍스트 밖으로 끌어 와서 호출하여 논리가 관련 빈에 머무를 수있게했습니다. – sourcedelica

5

봄 부팅 1.3.0이 또한 ApplicationListener<ApplicationReadyEvent>

예를 구현하여 수행 할 수 있기 때문에 파일 이름 src/main/resources/META-INF/spring.factoriesApplicationListener입니다. 예를 들어 : HTTP :

org.springframework.context.ApplicationListener=com.example.MyApplicationListener 

하지만, 내 경우에는, 난 단지 당신이 본 적이

그래서 난 application-<profile_name>.properties

context.listener.classes=com.example.MyApplicationListener 
관련 문제