Skip to content

Latest commit

 

History

History
157 lines (115 loc) · 8.3 KB

File metadata and controls

157 lines (115 loc) · 8.3 KB

Spring IOC에 대해서 설명해주세요.

목차

  1. Spring IoC 컨테이너란?
  2. Spring IoC 컨테이너 종류
  3. Spring IoC 컨테이너의 생명 주기

1. Spring IoC컨테이너란?

Spring에서의 IoC

  • 객체(Bean)의 생성과 의존관계에 대한 관리(Control)를 사용자가 직접 하는 것이 아닌 스프링 컨테이너(외부)가 책임지는 구조를 의미한다.
  • 스프링에서 IoC의 역할을 담당하고 있는 것이 IoC Container이다.

Container(컨테이너)란?

  • 스프링을 사용할 때 다루고자 하는 객체를 담는 공간을 컨테이너라고 한다.
  • 컨테이너는 객체의 생명주기를 관리하고 생성된 객체들에게 추가적인 기능을 제공한다.

IoC Continer란?

  • 스프링에서 객체(Bean)를 생성하고 의존성을 관리하는 컨테이너를 의미한다.

  • 즉, IoC컨테이너는 단순히 객체의 생성뿐아니라 의존성 주입까지 한다는 의미를 포함하고 있다고 보면 된다.

  • XML, Java Configuration, Annotation 등의 방식을 사용하여 IoC 컨테이너를 설정할 수 있고, IoC 컨테이너가 생성하는 객체의 종류나 의존성 등을 유연하게 관리할 수 있다.

  • IoC Container를 사용하지 않았을 경우

    • 자바 객체 생성 → 의존성 객체 생성(클래스 내부에서 생성) → 의존성 객체 메소드 호출
    • 사용자가 작성한 코드에 따라 객체를 생성하고 의존관계를 주입한다.
public class Hello{
 private Person person;

 public Hello(){
 person = new Person();
}
}
  • IoC Container를 사용한 경우
    • 스프링 객체 생성 → 의존성 객체 주입(제어권을 스프링에 위임하여 스프링이 만들어놓은 객체를 주입하게 한다) → 의존성 객체 메소드 호출
    • 사용자가 별도의 어노테이션만 선언해주면 스프링의 IoC컨테이너가 알아서 객체(Bean)를 생성하고 의존관계를 주입해준다.
@Component
public class Hello{
 private Person person;

@Autowired
 public Hello(Person person){
 this.person = person;
}
}

→ 스프링 IoC Container가 직접 객체를 생성하여 해당 객체에 주입 시켜주고 있다. 개발자가 해야 할 제어를 스프링 컨테이너에서 대신 해주고 있다. 그렇기에 제어의 역전(IoC)이라고 한다.

2. Spring IoC컨테이너의 종류

  • 스프링은 IoC를 구현하기위해 보통 DI(Dependency Injection)을 사용한다.
    • DI (의존성 주입) : 각 클래스 간의 의존 관계를 빈 설정 정보를 바탕으로 컨테이너가 자동으로 연결해주는 것이다.

IoC 컨테이너의 종류

  • BeanFactory

    • IoC Container의 기본이 되는 인터페이스로, Bean을 관리하는 역할을 한다.
    • Bean을 등록/생성/조회/반환한다.
    • 보통은 BeanFactory를 바로 사용하지 않고 구현체인 ApplicationContext를 사용한다.
  • ApplicationContext

    • BeanFactory를 구현하고 있는 클래스로, BeanFactory에 비해 더 많은 기능을 제공하고 있다.
      • 메시지 소스를 활용한 국제화 기능 (MessageSource 인터페이스)
        • 메시지에 대한 국제화를 제공하는 인터페이스이다.
        • 메세지 설정 파일을 모아서 각 국가마다 로컬라이징을 함으로써 각 지역에 맞춤 메시지를 제공할 수 있는 것이다.
        • 한국에서 들어오면 한국어로, 영어권에서 들어오면 영어로 출력한다.
      • 환경 변수 구분 기능(EnvironmentCapable인터페이스)
        • 로컬(내pc), 개발(테스트서버), 운영(실제 서비스) 등을 구분해서 처리
      • 애플리케이션 이벤트 (ApplicationEventPublisher 인터페이스)
        • 이벤트를 발행하고 구독하는 모델을 편리하게 지원 (’@EventListener’)
      • 편리한 리소스 조회 (ResourceLoader 인터페이스)
        • 파일, 클래스 패스, 외부 등에서 리소스를 편리하게 조회
    • ‘@Configuration’이 붙은 클래스들을 설정 정보로 등록해두고, ‘@Bean’이 붙은 메소드의 이름으로 Bean 목록을 생성한다.
    • 싱글톤(하나의 인스턴스를 공유하여 사용)으로 객체를 생성, 관리한다.

image

3. Spring IoC컨테이너의 생명주기

  • 생성 → 빈 설정 → 사용 → 소멸
  • IoC 컨테이너의 생명 주기는 애플리케이션이 시작될 때 시작되며, 애플리케이션이 종료될 때 함께 소멸한다.
  1. Resource 로딩
  • IoC 컨테이너가 사용할 설정 파일(설정 정보)을 로드하는 단계이다. 설정 파일에는 어떤 객체를 생성하고 어떻게 의존성을 가질 지에 대한 정보가 포함되어 있어서, 이 설명서를 보고 사용할 Bean 객체를 정의할 수 있다.
  • 이 단계에서 실제로 객체를 생성하지 않는다. 설정 파일의 정보들(Bean 객체 정보)을 메모리에 로드하고, 객체간의 의존성을 해결하는 일을 한다.
  1. Bean 설정
  • Bean 객체를 구성하는 메타 데이터를 읽어들인다.
  • 메타 데이터 내용으로는 Bean의 이름과 타입, 의존성, 생성자의 파라미터, 프로퍼티 값, 초기화와 소멸 메소드 등이 있다.
  • 이런 정보들을 읽어서 IoC컨테이너가 사용할 수 있는 형태로 변환한다.
  1. Bean 인스턴스화
  • Bean 설정 단계에서 변환한 정보를 기반으로 Bean 객체를 생성한다.
  1. 의존성 주입
  • 생성한 Bean 객체 간의 의존성을 주입한다.
  • Resource단계와 다른 점
    • Bean들 간의 의존관계를 검사하고 메모리에 로드 할 뿐이다.
    • 이번 단계에서는 객체가 생성되고, 실제로 Bean간의 의존성을 주입한다.
  1. Bean 초기화 콜백
  • Bean 인스턴스가 생성된 후에, IoC 컨테이너가 빈을 초기화하기 위한 콜백 메서드를 호출한다.
  • 초기화하는 이유는 생성자를 호출하는 것만으로 초기화할 수 없는 작업들이 존재하기 때문이다. 외부 리소스에 대한 연결 작업, 초기 데이터 로딩 작업과 같은 것들을 해야지만, 완전히 초기화되어 '사용 가능'한 상태가 될 수 있다
  • ‘@PostConstruct’ 사용
  1. Bean 사용

  2. Bean 소멸 콜백

  • 빈이 더 이상 필요하지 않을 때, IoC컨테이너는 빈의 소멸 메소드를 호출하고 해당 빈을 제거한다.
  • ‘@PreDestroy’ 사용
  1. Resource 해제(컨테이너 종료)
  • 컨테이너가 종료될 때 빈들도 함께 소멸된다.

[Reference]

질문 답변

1. 컨테이너는 어떤 추가적인 기능을 제공하나요?

  • 컨테이너마다 제공해주는 기능이 다르다.
  • 여기서 설명한 컨테이너는 IOC컨테이너이다.
  • 추가적인 기능
    • 빈의 생명주기 관리
    • 객체를 빈으로 등록, 생성, 조회, 반환
    • 국제화 기능
    • 환경변수 구분 기능
    • 애플리케이션 이벤트
    • 편리한 리소스 조회

2. 스프링컨테이너는 어떻게 객체를 싱글톤으로 생성, 관리하나요?

  • 각 ‘@Bean’이 붙은 메소드마다 Bean이 이미 스프링 컨테이너에 등록되어 있는 경우 새로운 Bean을 생성하지 않고, 스프링 컨테이너에서 찾아서 이미 존재하는 Bean을 반환해준다. 스프링 빈이 없으면 새롭게 생성해서 스프링 빈으로 등록하고 반환한다.

3. 스프링은 어떻게 의존성 객체의 생성 순서를 결정하나요?

  • ‘@Autowired’필드 명 매칭
    • 같은 타입 빈이 2개 이상 존재한다면 필드 이름으로 먼저 찾고, 중복된다면, 파라미터 이름으로 알맞은 빈을 의존성 객체로 생성한다.
  • ‘@Qulifier’끼리 매칭
    • 부가적인 이름을 붙여주고 생성자의 매개변수 앞에 ‘@Qualifier(부가적인 이름)’을 작성해주면 원하는 빈이 주입이 된다.
  • ‘@Primary’
    • 여러 빈이 존재한다면 ‘@Primary’가 붙은 빈이 우선권을 가진다.