티스토리 뷰
스프링 주요 기술에서 언급한 DI에 대해서 공부한 내용입니다.
의존성 주입? 의존관계 설정!
DI가 가장 흔하게 번역되어 사용되는 건 '의존성 주입' 혹은 '의존 오브젝트 주입'인데, 이는 DI의 의미가 무엇인지 잘 드러내주지 못합니다.
오브젝트의 레퍼런스가 전달될 뿐이지, 오브젝트는 다른 오브젝트에 주입될 수 없습니다.
용어는 동작방식보다는 의도를 가지고 이름을 짓는 것이 더 좋습니다.
그렇기 때문에 의존관계 주입 혹은 의존관계 설정이라는 번역이 제일 적절하다고 토비의 스프링에서 나와있습니다.
다음은 의존관계에 대해서 알아봅시다.
의존관계
두 개의 클래스 혹은 모듈이 의존관계에 있다고 말할 때에는 항상 방향성을 부여해줘야 합니다.
누가 누구에게 의존하는 관계에 있다는 걸 화살표를 통해 보여줍니다.
위 그림은 A가 B에 의존하고 있음을 나타냅니다.
의존하고 있다?
의존한다는 건, B에서 변경이 일어나면 A에 영향이 미친다는 걸 의미합니다.
대표적인 예로 A가 B를 사용하는 경우 즉, A에서 B에 정의된 메서드를 호출해서 사용하는 경우입니다.
런타임 의존관계
위 그림은 설계 모델 관점에서의 의존관계입니다.
하지만, 런타임 시에 오브젝트 사이에서 만들어지는 의존관계도 있습니다.
이를 런타임 의존관계 혹은 오브젝트 의존관계라고 합니다.
이전 포스팅에서도 언급했지만, 런타임 시점의 의존관계를 형성하려면 제 3의 존재가 필요합니다.
제 3의 존재, DI 컨테이너
이는 두 오브젝트 사이의 런타임 의존관계를 설정해주는 의존관계 주입 작업을 주도하는 존재입니다.
동시에 IoC 방식으로 오브젝트의 생성과 초기화, 제공 등의 작업을 수행합니다.
다음은 의존관계 주입을 위한 예시 코드입니다.
public class CustomerService {
private CustomerRepository customerRepository;
public CustomerService(CustomerRepository customerRepository) {
this.customerRepository = customerRepository;
}
}
보통 스프링+자바에서는 @RequiredArgsConstructor 어노테이션을 사용합니다.
@RequiredArgsConstructor
public class CustomerService {
private final CustomerRepository customerRepository;
}
의존관계 검색 vs 의존관계 주입
위에서 계속 의존관계 주입에 대해서 알아보았습니다.
다음은 의존관계 검색에 대해서 알아봅시다.
의존관계 검색은 자신이 필요로 하는 의존 오브젝트를 능동적으로 찾습니다.
런타임 시 의존관계를 맺을 오브젝트를 결정하는 것과 생성 작업은 이부 컨테이너에게 IoC로 맡깁니다.
하지만, 이를 가져올 때에는 메서드나 생성자를 통한 주입 대신 스스로 컨테이너에게 요청합니다.
이런 작업을 일반화한 스프링의 애플리케이션 컨텍스트라면 미리 정해놓은 이름을 전달해서 그 이름에 해당하는 오브젝트를 찾게 됩니다.
스프링의 IoC 컨테이너인 애플리케이션 컨텍스트는 getBean()이라는 메서드를 제공하여 의존관계 검색에 사용됩니다.
우리 개발자들은 대개 의존관계 검색보다는 의존관계 주입을 많이 사용합니다.
그럼 의존관계 검색은 언제 사용될까?
애플리케이션의 기동 시점에서 적어도 한 번은 의존관계 검색을 통해 오브젝트를 가져와야 합니다.
스태틱 메서드인 main()에서는 DI를 사용하여 오브젝트를 주입받을 방법이 없기 때문이죠.
서버에서도 사용자의 요청을 받을 때마다 서블릿에서 스프링 컨테이너에 담긴 오브젝트를 사용하려면 적어도 한 번은 의존관계 검색을 통해서 오브젝트들을 가져와야 합니다.
다행히 이런 서블릿은 스프링이 미리 실행될 때 만들어놓으므로 우리 개발자들은 신경 쓸 필요가 없습니다.
가장 중요한 점은 DI를 원하는 오브젝트는 먼저 자기 자신이 컨테이너가 관리하는 빈이 되어야 합니다.
결론
이번 포스팅에서는 의존관계에 대해서 가볍게 알아보았습니다.
다음 포스팅에서는 생성자가 아닌 다른 방법으로 의존관계를 주입할 수 있는지 알아보겠습니다.
'Sping Framework' 카테고리의 다른 글
Interceptor, Filter, AOP 차이 (0) | 2023.10.07 |
---|---|
스프링의 주요 기술 [1-2]. 애플리케이션 컨텍스트 (0) | 2023.02.07 |
스프링의 주요 기술 (0) | 2023.02.02 |
JPA에서의 bulk insert, bulk update test (0) | 2022.08.14 |
프로토타입과 스코프 [3]. 스코프 (0) | 2022.07.15 |
- Total
- Today
- Yesterday
- 디자인패턴
- AWS
- 코테
- 정규표현식
- BAEKJOON
- 이펙티브 자바
- Algorithm
- 객체지향
- node.js
- MSA
- 클린 코드
- Java
- 백준
- 테라폼
- JPA
- BOJ
- 프로그래머스
- kkoon9
- Spring
- Olympiad
- C++
- Kotlin
- kotest
- 이팩티브 자바
- 클린 아키텍처
- programmers
- 디자인 패턴
- Effective Java
- Spring Boot
- 알고리즘
일 | 월 | 화 | 수 | 목 | 금 | 토 |
---|---|---|---|---|---|---|
1 | 2 | 3 | 4 | |||
5 | 6 | 7 | 8 | 9 | 10 | 11 |
12 | 13 | 14 | 15 | 16 | 17 | 18 |
19 | 20 | 21 | 22 | 23 | 24 | 25 |
26 | 27 | 28 | 29 | 30 | 31 |