Spring 에서 Bean이란.
스프링이 처음 기동할때 스프링 컨테이너 안에 특정 annotation이 걸리거나 설정해둔 객체들이 올라가는데, 그 올라간것들을 Bean이라고 한다.
자세한 내용은 참고포스팅을 참고바란다.
하지만 너무 많은 Bean을 등록하게 될 경우에 Spring 기동이 오래 걸리고
자주 사용되지 않는 Bean등 몇몇의 Bean은 꼭 기동시 올라오지 않아도 되는 경우가 있다.
이럴 경우 Lazy 설정을 걸어서 나중에 등록이 되도록 할수가 있다.
Lazy란 게으른. 이라는 뜻으로 말그대로 게을러서 나중에 Bean이 등록이 된다.
방법은 간단하다. 늦게 뜨길 원하는 Bean에 @Lazy annotation 을 붙여주면 된다.
그리고 만약 의존성 주입을 받는 경우라면 Autowired와 함께 사용을 해서 주입해주면 된다.
아래 예제를 확인해보면
먼저 Lazy를 사용 안할 경우에
private final LazyTestComponent component; @PostMapping("/lazy") public String lazyApi(@RequestBody TestInDto inDto) { System.out.println("LazyTest 시작"); component.test(); System.out.println("LazyTest 끝"); return inDto.toString(); } |
@Component public class LazyTestComponent { public void test() { System.out.println("Lazy test method"); } @PostConstruct void init() { System.out.println("init Lazy test method"); } } |
PostConstruct 는 참고 포스팅 참고 바란다.
이럴 경우엔 /lazy를 호출하면 아래와 같은 출력이 찍힌다.
------springboot기동------
init Lazy test method
@@@여기서 /lazy호출시
LazyTest 시작
Lazy test method
LazyTest 끝
일단 스프링 기동이 되면서 Bean들은 전부 등록이 되어야하기에 LazyTestComponent 가 불리고 그때 init 함수가 바로 호출이 되기에 /lazy를 호출하기도 전에 init Lazy test method가 출력이 되었다.
그리고 실행 후 순서대로 출력이 찍혔다.
이제 Lazy 를 적용해보면 코드가 이렇게 바뀐다.
@Autowired @Lazy private LazyTestComponent component; @PostMapping("/lazy") public String lazyApi(@RequestBody TestInDto inDto) { System.out.println("LazyTest 시작"); component.test(); System.out.println("LazyTest 끝"); return inDto.toString(); } |
@Component @Lazy public class LazyTestComponent { public void test() { System.out.println("Lazy test method"); } @PostConstruct void init() { System.out.println("init Lazy test method"); } } |
이러고 호출하면 출력이 다음과 같다.
------springboot기동------
@@@여기서 /lazy호출시
init Lazy test method
LazyTest 시작
Lazy test method
LazyTest 끝
정상적으로 스프링이 기동이 되고 Lazy가 걸려있는 Bean이어서 스프링 기동시 생성이 되지 않는다.
그리고 /lazy로 인해서 호출이 되니까 그제서야 init method가 돌면서 Bean이 등록이 되었다.
이렇게 Lazy annotation으로 늦게 Bean이 등록되도록 설정이 가능하다.
그리고 특정 Bean들이 아닌 모든 Bean들에 대해서 Lazy로 설정 하는 방법도 있다.
2가지 방법이 있다.
1. yml 파일에 설정하기
yml 파일에 spring.main.lazy-initialization= true 를 설정해준다.
2. 모든 빈을 호출해서 SetLazy 를 true로 해준다.
해당 클래스는 springboot 내에 main 메서드와 동일한 위치에 시켜주고,
import org.springframework.beans.BeansException; import org.springframework.beans.factory.config.BeanFactoryPostProcessor; import org.springframework.beans.factory.config.ConfigurableListableBeanFactory; import org.springframework.context.annotation.Configuration; @Configuration public class LazyInitBeanFactoryPostProcessor implements BeanFactoryPostProcessor { @Override public void postProcessBeanFactory(ConfigurableListableBeanFactory beanFactory) throws BeansException { for (String beanName : beanFactory.getBeanDefinitionNames()) { beanFactory.getBeanDefinition(beanName).setLazyInit(true); } } } |
이렇게 등록 해주면 된다.
참고 포스팅
https://thenicesj.tistory.com/269
https://thenicesj.tistory.com/320
https://thenicesj.tistory.com/601
'IT > Java' 카테고리의 다른 글
[Java] ASCII 문자 숫자 변환 코드 (50) | 2023.08.29 |
---|---|
Statement / preparedStatement 차이 (53) | 2023.08.28 |
SpringJDBC에서 DataSource, RowMapper란? (44) | 2023.08.24 |
[Java] Scope란? (52) | 2023.08.23 |
[Spring] Devtools 이란? (23.08.19) (12) | 2023.08.20 |
댓글