SpringBean & SpringContainer 에 대해서
도입
자주 사용하는 Spring Container 에 대해서 알아보려고 한다.
여태 SpringBoot 를 사용하면서, 정리한 적이 없어 정리를 해보려고 한다.
Spring Bean
Spring Bean 이란?
Spring Bean 이라는 특별한 이름을 가지고 있지만, 결국
자바 인스턴스를 말한다. 굳이 Spring Bean 이라고 차별화를 둔 이유는
특정 객체를 프레임워크 ( Spring ) 에서 관리하기 위해서다.
프레임워크가 관리하는 객체와 사용자가 관리하는 객체의 차이점에 대해서 간단히 알아보면 다음과 같다.
사용자가 관리하는 객체
new 연산자를 사용하여, 사용자가 직접관리
- 객체의 생성, 초기화, 메모리 해제를 개발자가 명시적으로 제어
- 의존적인 관계에서 필요한 객체를 직접 생성하거나, 찾아서 할당해야한다.
프레임워크가 관리하는 객체
객체의 생명주기를 프레임 워크가 관리
- 프레임워크가 객체를 제어함으로, 개발자는 객체 사용에 집중 할 수 있음 ( Inversion Of Control )
- 다른 객체에서 해당 객체를 필요로 하면 자동으로 객체를 할당 한다. ( Dependency Inejection )
Spring Bean 은 스프링 프레임워크가 관리하는 자바 객체 이며
프레임워크가 객체를 관리할 때 얻는 기능들 ( IOC, DI )을 활용하여
효과적인 어플리케이션 개발을 할 수 있다.
Spring Bean 의 특징
Spring Bean 의 다른 특징들에 대해서도 알아보자.
1. POJO 기반
특정 인터페이스를 구현하거나, 상속을 받을 필요가 없는 일반적인 자바 객체이다.
2. 의존성 주입 대상
프레임워크에서 생명주기를 관리하며, 다른 Spring 빈이 특정 빈 을 필요할때,
자동으로 빈을 할당해준다.
3. Scope 설정 가능
prototype, request, session, application, websocket, singleton 등 다양한
스코프를 지원한다.
- prototype
Bean 요청 할때 마다 새로운 인스턴스 생성
- request
웹 요청이 올때 마다 Bean 생성, 요청 종료 시 Bean 소멸
- session
웹 요청에서 하나의 사용자 세션이 연결되고 종료될 때까지 해당 Bean의 인스턴스가 유지
- application
웹 어플리케이션이 연결되고 종료될 때까지 해당 Bean의 인스턴스가 유지
- websocket
하나의 웹소켓 세션이 연결되고 종료될 때까지 해당 Bean의 인스턴스가 유지
- singleton
기본 스코프이며, 컨테이너와 생명주기가 같고 하나의 인스턴스만 존재
4. AOP 적용에 용이
빈들이 프레임워크로 인해 관리 되기 때문에, 횡단 관심사를
비지니스로직에 적용하지 않고 AOP 적용이 쉬움
5. Singleton
기본적으로 Spring Bean 은 Singleton Scope 으로 사용되며,
어플리케이션 전역에서 단일 인스턴스만 사용한다.
- SingleTon 인 이유?
대부분 Application 컴포넌트는 Stateless 이기 때문에, 매번 생성하는 것은 비효율적임으로
- 생명 주기
Scope 가 SingleTon 일 경우, Application 의 생명 주기가 같다.
이러한 Spring Bean의 특징들은 Spring Container (IoC/DI 컨테이너)가
Spring Bean을 효율적으로 관리하기 때문에 가능하다.
이제 Spring Container 에 대해서 알아보자.
Spring Container
Spring Container 란 ?
Spring Application 의 핵심이며, 객체 ( Spring Bean ) 의 생명 주기를
관리하고 의존성 주입을 하는 기술이다.
ApplicationContext
Spring Container 의 인터페이스인 BeanFactory
인터페이스를
확장한 인터페이스로 많은 기능을 제공한다. 여기서 BeanFactory 는
가장 기본적인 컨테이너이다.
- eager Loading 방식
컨테이너가 시작될 때 모든 Spring Bean 을 SingleTon Bean 으로 초기화 한다.
- 다양한 기능 제공
국제화, 이벤트 발행, 리소스 로딩, AOP, Web Application 컨텍스트등
다양한 것을 지원한다.
여러가지 구현체가 있지만 주로AnnotationConfigApplicationContext
( 자바 어노테이션 기반 설정 ) 구현체를 권장하고 있다.
Spring Container 동작 방식
개발자가 정의한 Bean 설정 ( XML, Java Config, Annotation … ) 을 읽어서
Spring Bean 생명 주기를 관리한다.
1. Container 초기화
ApplicaitonContext 가 시작하면서, Bean 설정 정보를 로드한다
2. Bean 생성
Spring Bean 정의에 따라 Spring Bean 을 생성한다.
3. 의존성 주입
생성된 Spring Bean 의 필드,세터, 생성자 ( 권장 ) 등을 이용하여 의존하는
다른 Bean 을 주입한다.
→ 컨테이너가 직접 의존 관계를 연결하기 때문에, 개발자가 결합도에 대한 신경을 쓰지 않아도됨
4. 초기화 콜백
Spring Bean 의 의존성 주입이 완료된 후 Bean 이 사용될 주닙가 되었을 때,
특정 초기화 작업을 수행할 수 있도록 콜백 메서드를 호출
5. 소멸 콜백
컨테이너가 종료 될 때, 빈을 소멸하기 전 정리 작업을 수행
여기서 정리 작업이란, DB Connection 을 종료하거나 , File Stream 닫기
네트워크 소켓 해제등이 있다.
6. 컨테이너 종료
컨테이너가 종료되고 빈 객체들이 메모리에서 해제된다.
Spring Bean 등록 방법
Spring Bean 을 등록 방법은 크게 3가지가 있다.
1. 컴포넌트 스캔 ( Component Scan )
현재 가장 많이 사용 되는 방법이다.@Component
, @Service
, @Repository
, @Controller
, @Configuration
, @Bean
등의
스테레오 타입 Annotation 이 붙은 클래스를 조회해서 Bean 으로 등록한다.
개발 생산성이 높고 유지 보수가 용이하다.
Java
@Component
@RequiredArgsConstructor
public class JwtFilter extends OncePerRequestFilter {
private final JwtHandler handler;
private static final List PUBLIC_PATHS = Arrays.asList(
"/members/login",
"/members",
"/members/reissue"
);
...
2. XML 설정 파일 사용
XML 파일에
Bean 정의를 XML 에 작성하기 때문에 자바 코드와 분리하여 사용할 수 있지만,
그만큼 번거로우며 Refactoring 이 어렵다.
XML
글을 마치며
이처럼 Spring Bean과 Spring Container는 스프링 프레임워크의 근간을 이루는 핵심 개념이며
덕분에 더 쉽고 개발에 집중하며 Application 을 개발 할 수 있게 되었다.