먼저 DI에 대해서 다시 한번 짚고 넘어가보자면,
DI(Dependency Injection)이란, 어떤 코드에서 필요로 하는 의존성을 외부에서 주입(injection)하는 방법을 말합니다.
DI의 목적은 한 코드 내에서 생성과 구현의 책임을 분리하기 위함이고,
이를 통해 런타임 의존성을 갖게 되어 결합도를 낮추고 유연한 코드 설계를 가능하게 해 주는 기법입니다.
DI 설명을 위해 예시 코드로 Adder(두 수를 더하는 클래스)를 작성했습니다.
DI의 세 가지 방법 - 1. setter 주입
public class Adder {
private int number1;
private int number2;
public void setNumber1(int value){
this.number1 = value;
}
public void setNumber2(int value){
this.number2 = value;
}
}
- setter 주입이란, 말 그대로 setter를 통해 값을 변경하는 방법입니다.
- setter 메서드의 파라미터로 변경할 값을 주입하여, 이를 업데이트합니다.
- 하지만 setter 주입을 사용할 경우 외부에서 손쉽게 내부 필드에 접근하여 값을 변경할 수 있게 되므로 권장하지 않습니다.
DI의 세 가지 방법 - 2. 필드 주입(@Autowired)
public class Adder {
@Autowired
private int number1;
@Autowired
private int number2;
}
- Spring에서 필드 주입은 @Autowired 어노테이션을 통해 이루어집니다.
- @Autowired를 이용하면, 해당 어노테이션이 붙은 필드에 스프링 빈 객체를 매핑하여 자동으로 의존성 주입을 해 줍니다.
- 의존 관계가 외부로 명확하게 드러나지 않는다는 단점이 있습니다. 즉, 스프링 컨테이너와 강하게 결합할 수 있는 소지가 있습니다.
- final로 선언된 필드에는 @Autowired 사용이 불가능합니다.
- 의존성 주입을 위한 DI 컨테이너가 반드시 존재해야 합니다.
DI의 세 가지 방법 - 3. 생성자 주입
public class Adder {
private int number1;
private int number2;
public Adder(int value1, int value2) {
this.number1 = value1;
this.number2 = value2;
}
}
- 생성자를 통해 의존성 주입(DI)를 구현할 수 있습니다.
- 생성자 파라미터를 통해 의존성을 주입받습니다.
결론적으로, 위 세 가지 방법 중 생성자 주입을 사용하자.
위에서 소개했던 DI의 세 가지 방법들 중, 생성자 주입을 사용하는 것이 가장 바람직하다. 그 이유는 무엇일까?
1. 의존관계 설정은 단 한번만 일어난다.
- setter 주입의 경우, 항상 변경 가능성을 내포하고 있다.
- 그러나 생성자 주입의 경우에는, 해당 코드가 단 한번만 실행된다는 것을 보장합니다.
2. final로 선언된 필드에도 의존성 주입이 가능하다는 점이다.
- final 키워드는 상수 필드를 선언할 때 사용하며, 상수 필드는 선언과 함께 반드시 초기화가 함께 이루어져야 한다.
- 만일 개발자의 실수로, 외부에서 의존성을 주입하는 코드가 누락되었다면 final로 선언된 필드의 경우 컴파일 타임에 해당 실수를 잡아낼 수 있습니다.
'CS > Spring' 카테고리의 다른 글
[Spring] @NoArgsConstructor, @RequiredArgsConstructor, @AllArgsConstructor의 차이점 간단 정리. (0) | 2023.04.24 |
---|---|
[Spring] 스프링에서 빈 객체를 등록하는 방법(@Bean, @Component) (0) | 2023.04.14 |
[Spring] 비즈니스 로직이란? (0) | 2023.04.08 |
[Spring] Controller, Service, Repository (0) | 2023.04.08 |
[Spring] Entity, DTO, VO 무슨 차이야? (0) | 2023.04.07 |