Spring IoC, DI

EUNJI LEE·2023년 7월 29일
0

Spring

목록 보기
4/13

IoC(Inversion of Controller)

IoC는 프로그램이 동작하는데 메소드나 객체의 호출 작업을 개발자가 아닌 프로그램이 작동하는 컨테이너에서 직접 관리하는 것을 말한다. Spring은 IoC 구조를 통해서 프로그램 동작 시 필요한 객체의 생성부터 생명 주기까지를 직접 수행한다.

단순하게 제어의 역전이라고 하며 객체의 의존성을 역전시켜서 객체 간이 결합도를 낮추고 유연한 코드를 작성할 수 있도록 한다. IoC 방식으로 프로그램이 동작하면 코드의 중복이 줄어 가독성을 높일 수 있고 유지 보수 또한 수월해진다는 장점이 있다.

IoC 컨테이너 역할

  1. 객체의 생명주기와 의존성 관리
  2. VO(DTO, POJO) 객체의 생성, 초기화, 소멸 등 처리를 담당
  3. 개발자가 직접 객체를 생성할 수 있지만 권한을 컨테이너 넘김으로써 소스 코드 주현 시간을 단축

Bean

스프링이 IoC 방식으로 관리하는 클래스들을 의미한다. 빈은 스프링이 직접 생성과 제어를 담당하게 된다.

Bean Factory

스프링의 IoC를 담당하는 핵심이 되는 컨테이너로 Bean을 등록, 생성, 조회, 반환하는 기능을 담당한다. Bean들을 관리하는 역할을 담당하는 컨테이너라고 할 수 있다. 사용할 Bean을 구하는 메소드로getBean()를 제공한다. 등록된 Bean 객체를 반환하며 첫 번째 파라미터로 Bean의 이름, 두 번째 파라미터로 Bean의 타입을 작성할 수 있고 둘 중 하나만 작성해도 해당하는 Bean을 반환한다.

ApplicationContext

BeanFactory를 확장한 IoC 컨테이너로 Bean을 등록하고 관리하는 기능은 BeanFactory와 동일하지만 스프링이 제공하는 각종 부가 서비스를 추가로 제공한다. BeanFactory 인터페이스를 구현한 최상위 구현체이다.

GenericXmlApplicationContext

ApplicationContext를 구현한 클래스로 일반적인 xml 형태의 문서를 읽어서 해당 문서에 등록된 Bean들을 관리하는 컨테이너 역할을 한다.

GenericXmlApplicationContext context
	=new GenericXmlApplicationContext("classpath:applicatonContext.xml");
Student student=context.getBean("student",Student.class);
//해당 이름의 Bean을 해당 클래스 타입으로 반환

Student student=context.getBean(Student.class);
//해당 클래스 타입의 Bean을 반환

Student student=(Student)context.getBean("student");
//해당 이름의 Bean을 Object 타입으로 반환

Configuration metadata

ApplicationContext 혹은 BeanFactory가 IoC를 적용하기 위해서 사용하는 설정 정보들을 말한다. Configuration metadata(설정 메타 정보)는 IoC 컨테이너에 의해 관리되는 Bean 객체를 생성하고 구성할 때 사용한다.

Spring DI(의존성 주입)

DI(Dependency Injection)은 IoC 구현의 핵심 기술이라고 할 수 있는데 사용하는 객체를 직접 생성해서 만드는 것이 아니라 컨테이너가 Bean의 설정 정보를 읽어와서 자동으로 해당 객체에 연결하는 것을 의미한다.

즉 등록된 Bean들을 필요한 시점에 저장해두는 것을 말하는데 이렇게 의존성 주입을 하게 되면 해당 객체를 수정해야 할 상황이 생겼을 때 소스 코드의 수정을 최소화할 수 있게 된다.

DI의 장점

  1. 개발자가 작성해야 할 코드가 단순해진다.
  2. 객체 간의 결합도(종속 관계)가 낮아지면서 유연성이 높아진다.

Spring DI 종류

Setter 메소드

의존성 주입을 받는 Setter 메소드를 만들고 이를 통해서 의존성 주입한다. Setter 메소드를 통해서 의존 관계가 있는 Bean을 주입하기 위해서는 <property>태그를 이용할 수 있다.

<bean id="ref에 들어갈 이름" class="주입할 객체(패키지명 포함)"/>
<bean id="객체 이름" class="Bean으로 등록할 클래스(패키지명 포함)">
	<property name="사용할 이름" value="이름에 들어갈 값"/>
	<property name="사용할 이름" ref="의존성 주입할 객체"/>
<bean>
<!-- example -->
<beans:bean id="dept" class="com.bs.spring.beantest.Department"/>
<beans:bean id="emp" class="com.bs.spring.beantest.Employee" 
	 	init-method="initialMethod" destroy-method="destroyMethod">
	 <beans:property name="name" value="Lee"/>
	 <beans:property name="age" value="26"/>
	 <beans:property name="address" value="서울"/>
	 <beans:property name="salary" value="3000000"/>
	 <beans:property name="dept" ref="dept"/>
</beans:bean>

생성자 이용

필요한 의존성을 포함하는 클래스에 생성자를 만들어놓고 이를 통해서 의존성을 주입한다. <constructor-arg> 태그를 이용해서 의존성을 주입할 수 있고 해당 방식은 생성자의 파라미터를 이용하기 때문에 한 번에 여러개의 객체 주입이 가능하다. 필드 선언 순서에 따라 index 속성을 통해서도 접근할 수 있다.

<bean id="ref에 작성할 이름" class="해당 객체 이름(패키지 포함)"/>
<bean id="불러올 객체 이름" class="클래스명(패키지 포함)">
	<constructor-arg index="0" value=""/>
	<constructor-arg index="1" ref="주입할 객체"/>
</bean>
<!-- example -->
<beans:bean id="dept" class="com.bs.spring.beantest.Department">
	 <beans:constructor-arg index="0" value="1"/>
	 <beans:constructor-arg index="1" value="개발부"/>
	 <beans:constructor-arg index="2" value="판교"/>
</beans:bean>
<beans:bean id="emp2" class="com.bs.spring.beantest.Employee">
	 <beans:constructor-arg index="0" ref="dept"/>
</beans:bean>
profile
천천히 기록해보는 비비로그

0개의 댓글