컨트롤러를 최신 주석 버전으로 변환하고 있습니다. 이전 버전에서는 다음을 사용하여 springmvc-servlet.xml에서 init 메소드를 지정했습니다.
<beans>
<bean id="myBean" class="..." init-method="init"/>
</beans>
주석 버전을 사용하여 초기화 방법을 어떻게 지정할 수 있습니까?
답변
당신이 사용할 수있는
@PostConstruct
public void init() {
// ...
}
답변
또는 클래스가 InitializingBean
인터페이스를 구현 afterPropertiesSet()
하여 Bean이 생성 될 때 ApplicationContext가 호출 할 콜백 함수 ( ) 를 제공하도록 할 수 있습니다 .
답변
Spring에서 초기화 프로세스를 가로채는 방법에는 여러 가지가 있습니다. 모든 bean을 초기화하고 autowire / inject해야한다면 적어도 두 가지 방법이 있습니다. 나는 두 번째 testet 만 가지고 있지만 둘 다 똑같이 작동한다고 믿습니다.
@Bean을 사용하는 경우 이와 같이 initMethod로 참조 할 수 있습니다.
@Configuration
public class BeanConfiguration {
@Bean(initMethod="init")
public BeanA beanA() {
return new BeanA();
}
}
public class BeanA {
// method to be initialized after context is ready
public void init() {
}
}
@Component를 사용하는 경우 이와 같이 @EventListener로 주석을 달 수 있습니다.
@Component
public class BeanB {
@EventListener
public void onApplicationEvent(ContextRefreshedEvent event) {
}
}
제 경우에는 Spring Boot가 선택된 프레임 워크 인 IoC / DI를 사용하는 레거시 시스템이 있습니다. 이전 시스템은 테이블에 많은 순환 종속성을 가져 오므로 setter-dependency를 많이 사용해야합니다. setter에 의한 autowiring / injection이 아직 완료되지 않았기 때문에 @PostConstruct를 신뢰할 수 없기 때문에 두통이 생겼습니다. 순서는 생성자, @PostConstruct, autowired setter입니다. 모든 빈에 대해 “동일한”시간에 마지막으로 실행되는 @EventListener 주석으로 해결했습니다. 이 예제는 InitializingBean의 구현도 보여줍니다.
서로 종속성이있는 두 개의 클래스 (@Component)가 있습니다. 이 예제에서는 클래스 중 하나만 표시하기 위해 동일하게 보입니다.
@Component
public class BeanA implements InitializingBean {
private BeanB beanB;
public BeanA() {
log.debug("Created...");
}
@PostConstruct
private void postConstruct() {
log.debug("@PostConstruct");
}
@Autowired
public void setBeanB(BeanB beanB) {
log.debug("@Autowired beanB");
this.beanB = beanB;
}
@Override
public void afterPropertiesSet() throws Exception {
log.debug("afterPropertiesSet()");
}
@EventListener
public void onApplicationEvent(ContextRefreshedEvent event) {
log.debug("@EventListener");
}
}
컨테이너가 시작될 때 호출 순서를 보여주는 로그 출력입니다.
2018-11-30 18:29:30.504 DEBUG 3624 --- [ main] com.example.demo.BeanA : Created...
2018-11-30 18:29:30.509 DEBUG 3624 --- [ main] com.example.demo.BeanB : Created...
2018-11-30 18:29:30.517 DEBUG 3624 --- [ main] com.example.demo.BeanB : @Autowired beanA
2018-11-30 18:29:30.518 DEBUG 3624 --- [ main] com.example.demo.BeanB : @PostConstruct
2018-11-30 18:29:30.518 DEBUG 3624 --- [ main] com.example.demo.BeanB : afterPropertiesSet()
2018-11-30 18:29:30.518 DEBUG 3624 --- [ main] com.example.demo.BeanA : @Autowired beanB
2018-11-30 18:29:30.518 DEBUG 3624 --- [ main] com.example.demo.BeanA : @PostConstruct
2018-11-30 18:29:30.518 DEBUG 3624 --- [ main] com.example.demo.BeanA : afterPropertiesSet()
2018-11-30 18:29:30.607 DEBUG 3624 --- [ main] com.example.demo.BeanA : @EventListener
2018-11-30 18:29:30.607 DEBUG 3624 --- [ main] com.example.demo.BeanB : @EventListener
보시다시피 @EventListener는 모든 것이 준비되고 구성된 후에 마지막으로 실행됩니다.
답변
public class InitHelloWorld implements BeanPostProcessor {
public Object postProcessBeforeInitialization(Object bean,
String beanName) throws BeansException {
System.out.println("BeforeInitialization : " + beanName);
return bean; // you can return any other object as well
}
public Object postProcessAfterInitialization(Object bean,
String beanName) throws BeansException {
System.out.println("AfterInitialization : " + beanName);
return bean; // you can return any other object as well
}
}