2022. 10. 13. 14:22ㆍJAVA/Spring
1. SpringApplication Events and Listeners
일반적인 ContextRefreshedEvent 클래스와 같은 스프링 프레임워크 이벤트들뿐만 아니라 SpringApplication 클래스는 몇가지 추가적인 이벤트들을 전송합니다.
빈으로 등록할 수 없는 리스너
몇몇 이벤트들은 ApplicationContext가 생성되기 전에 발생됩니다. 그래서 이러한 이벤트들은 @Bean으로 등록할 수 없습니다. 대신 다음과 같은 방법으로 리스너를 등록합니다.
- SpringApplication.addListeners() 메서드를 이용한 방법
- SpringApplicationBuilder.listeners() 메서드를 이용한 방법
- META-INF/spring.factories 파일에 리스너 참조를 추가하는 방법
리스너 생성 및 등록 (addListeners)
1. 리스너 클래스를 생성하고 빈으로 등록합니다. 그리고 ApplicationListener 인터페이스를 구현합니다.
@Component
public class ApplicationStartingEventListener implements ApplicationListener<ApplicationStartingEvent> {
@Override
public void onApplicationEvent(ApplicationStartingEvent event) {
System.out.println("=============================");
System.out.println("Application is Starting");
System.out.println("=============================");
}
}
2. 애플리케이션 리스너중 ApplicationStartingEvent는 ApplicationContext가 생성되기 이전에 발생하는 이벤트입니다. 따라서 빈으로 등록해도 리스너가 작동하지 않습니다. 따라서 리스너를 직접 등록해주어야 합니다.
@SpringBootApplication
public class SpringbootUtilizationApplication {
public static void main(String[] args) {
SpringApplication app = new SpringApplication(SpringbootUtilizationApplication.class);
app.addListeners(new ApplicationStartingEventListener());
app.run(args);
}
}
3. SpringApplication을 실행하여 ApplicationContext가 생성되기 이전에 리스너가 실행되는지 확인합니다.
만약 애플리케이션 리스너의 실행시점이 ApplicationContext 생성 이후라면 빈으로 등록하면 스프링 프레임워크가 자동으로 리스너를 실행시킬 것입니다.
SpringApplicationBuilder를 이용한 리스너 등록
new SpringApplicationBuilder()
.sources(SpringbootUtilizationApplication.class)
.listeners(new ApplicationStartingEventListener())
.run(args);
META-INF/spring.factories 파일에 리스너 참조를 추가하는 방법
만약 SpringApplication 인스턴스나 SpringApplicatoinBuilder와 같이 명시적으로 리스너를 추가하지 않고 한 파일에 많은 리스너를 저장해두고 싶다면 다음과 같은 방법을 사용할 수 있습니다.
META-INF/spring.factories 파일을 프로젝트에 추가하고 "org.springframework.context.ApplicationListener" 키 값을 사용해서 리스너를 참조시킵니다.
1. resources 디렉토리에 META-INF 디렉토리 생성후 spring.factories 파일을 생성
2. ApplicationListener 키값을 사용해서 리스너를 참조시킴
org.springframework.context.ApplicationListener=kr.yh.springapplication02.ApplicationStartingEventListener
3. 다음과 같이 SpringApplication 인스턴스에 리스너를 따로 추가하지 않고 실행하여 리스너가 ApplicationContext 생성 이전에 수행되는지 확인합니다.
2. Application Events 실행 순서
애플리케이션 이벤트들은 애플리케이션 실행시 다음과 같은 순서로 전송됩니다.
- ApplicationStartingEvent
- 애플리케이션이 실행되고나서 가능한 빠른 시점에 발행됨
- Environment와 ApplicationContext는 준비되지 않았지만 리스너들은 등록이 되었음
- 이벤트 발행 source로 SpringApplication이 넘어오는데, 이후 내부 상태가 바뀌므로 내부 상태의 변경은 최소화해야함
- ApplicationEnvironmentPreparedEvent
- 애플리케이션이 실행되고, Environment가 준비되었을때 발행됨
- ApplicationPreparedEvent
- 애플리케이션이 시작되고, 애플리케이션 컨텍스트가 완전히 준비되었지만 refresh되기 전에 발행됨
- 빈 정보들은 불러와졌으며 Environment 역시 준비가 된 상태임
- ApplicationStartedEvent
- 애플리케이션 컨텍스트가 refresh 되고나서 발행됨
- ApplicationRunner와 CommandLineRunner가 실행되기 전의 시점임
- ApplicationReadyEvent
- 애플리케이션이 요청을 받아서 처리할 준비가 되엇을때 발행됨
- 이벤트 발행 source로 SpringApplication이 넘어오는데, 이후에 초기화 스텝이 진행되므로 내부 변경은 최소화해야함
- ApplicationFailedEvent
- 애플리케이션이 실행에 실패했을때 발행됨
References
https://docs.spring.io/spring-boot/docs/2.1.6.RELEASE/reference/html/boot-features-spring-application.html#boot-features-application-events-and-listeners
[Spring] SpringBoot 실행 후에 초기화 코드를 넣는 3가지 방법과 이벤트 리스너(CommandLineRunner, ApplicationRunner, EventListener)
'JAVA > Spring' 카테고리의 다른 글
[Springboot] 23. SpringApplication #4 Application Exit & Admin Features (0) | 2022.10.14 |
---|---|
[Springboot] 23. SpringApplication #3 Web Environment (0) | 2022.10.13 |
[Springboot] 23. SpringApplication #1 Banner, Customizing (0) | 2022.10.12 |
[Spring] ResourceLoaderAware 인터페이스 (0) | 2022.10.04 |
[Spring] ResourcePatternResolver 인터페이스 (0) | 2022.10.03 |