티스토리 뷰
의존관계 주입 방법의 종류
1. 생성자 주입
생성자를 통해 의존관계를 주입받는다. 생성자 호출 시점에 단 1번 호출되는 것이 보장된다.
불변, 필수 의존관계에서 사용한다. -> 수정할 수 있는 기능을 추가하지 않는 것이 중요
생성자가 하나인 경우 @Autowired를 사용하지 않아도 스프링 컨테이너가 자동으로 의존관계 주입한다.
2. 수정자(setter) 주입
setter로 필드의 값을 변경하는 수정자 메서드를 통해 의존관계 주입 ( 메서드명은 set필드명 )
선택, 변경가능 의존관계에서 사용한다. -> 호출하여 변경할 수 있는 경우
+) 자바빈 프로퍼티 규약 -> 필드의 값을 직접 변경하지 않고 get, set 메서드를 통해 읽고 수정하는 내용
3. 필드 주입
필드에 바로 의존관계를 주입시키는 방법
외부에서 변경이 불가능하기 때문에 권장하는 방법이 아님 -> new로 객체를 만들어도 접근이 안되기에 null이 된다
4. 일반 메서드 주입
말 그대로 메서드를 만들어서 주입 받을 수 있다.
한 번에 여러 필드를 주입받을 수 있지만, 잘 안쓴다 ( setter랑 비슷, 쓸거면 생성자 쓰자 )
옵션 처리
주입할 스프링 빈이 없어도(목적지) 동작해야 할 때가 있다. -> 오류를 발생하지 않고
이때 @Autowired(required = false) 로 처리해주면 오류가 발생하지 않는다. 단, 호출도 되지 않는다.
생성자 주입을 선택해라! (사용해라)
위에서 나온 의존관계 주입 중 생성자 주입을 강조한다. DI 프레임워크 대부분이 생성자 주입을 권장하기 때문
불변하게 설계할 수 있다(수정자 주입처럼 값이 변하지 않을 수 있음을 보장)
누락하지 않을 수 있다
테스트 진행 시 의존관계 주입을 누락하지 않고 (까먹지 않고) 테스트 할 수 있다
생성자 주입때 누락 시 컴파일 오류가 발생하기 때문
final 키워드를 사용할 수 있다.
오직 생성자 주입만이 필드값을 final로 선언할 수 있다.
생성자에서 값 설정을 누락할 경우 오류를 쉽게 찾을 수 있다.
롬복(loombok)
생성자 주입이 좋은 것을 알겠는데.. 필드와 생성자 코드를 반복 작성하는 것이 귀찮음을 느껴버린 개발자님들
생성자, getter, setter 메서드를 생성해주는 롬복을 알아보자
롬복 사전 설정
그리고 설정 - 빌드,실행,배포 - 컴파일러 - 어노테이션 프로세서 에서 어노테이션 처리 활성화를 체크해야 함
@Getter - 필드 getter 메서드를 생성해준다.
@Setter - 필드 setter 메서드를 생성해준다.
@RequiredArgsConstructor - 필드 중 final이 붙은 값들로 생성자를 생성해준다.
@NoArgsConstructor - 매개변수가 없는 생성자를 생성해준다.
생성자를 1개만 두고 사용한다면 @Autowired 생략과 롬복 기능을 통해 위처럼 코드를 간결하게 짤 수 있다.
조회할 빈이 2개라면 발생하는 일
@Autowired 는 빈을 Type으로 조회한다.
그렇다면 2개 이상의 빈이 조회되면 저번 시간에 공부한 빈 충돌이 발생한다.
ex) DiscountPolicy의 FixDiscountPolicy와 RateDicountPolicy
수동으로 빈 이름을 지정해주는 것이 아닌 자동 주입으로는 해결 방안이 없을까? ( 있다! )
1. @Autowired의 필드 명 매칭
@Autowired는 Type을 먼저 조회(자식이 있다면 자식까지)하고, 그 이후 필드 명과 파라미터 명으로 조회
즉, 필드명을 DiscountPolicy rateDiscountPolicy나 파라미터 명을 rateDiscountPolicy로 한다면
Type 조회 후 결과로 여러 빈 중 이름 매칭을 추가로 진행한다.
2. @Qualifier 사용
@Qualifier는 빈 이름에 별명을 부여한다고 생각해보자 ( 빈 이름을 변경하는게 아니다 )
이 경우 @Qualifier가 붙은 것들끼리 매칭을 하고, 없다면 스프링 빈 이름으려 매칭을 한다. ( 이후에는 예외.. )
3. @Primary 사용
우선순위를 지정하는 방식이다.
@Qualifier와 비슷한 점이 많지만, 찾는 파라미터를 간결하게 쓸 수 있기에 @Primary를 사용한다.
+) @Primary와 @Qualifier가 동시에 사용된다면 더 상세한 @Qualifier가 우선으로 동작한다
설정 정보를 자동으로 vs 수동으로 어떻게 판단할까
결론적으로는 자동으로 주입하는 추세
@Component를 넣어주는 것이 @Configuration 설정 정보에서 @Bean으로 객체를 생성하여 주입하는 것보다
더 간단하고, 설정 정보를 가볍게 관리할 수있다.
수동이 더 필요한 상황은?
애플리케이션의 업무 로직과 기술 지원 로직
업무 로직 빈 - 컨트롤러, 비즈니스 로직이 있는 서비스, 데이터 계층 로직을 처리하는 리포지토리 등이 업무 로직
기술 지원 빈 - 기술적인 문제가 공통 관심사(AOP, 메서드들의 실행 시간과 같은)를 처리할 때 사용
업무 로직을 지원하기 위한 하부 기술이나 공통 기술들이다.
여기서 업무 로직은 방대한 양이고, 유사한 패턴이기에 자동 기능을 사용하는 것이 좋다.
반대로 기술 지원 로직은 양이 상대적으로 적고, 광범위한 영향을 준다.(모든 메서드 시간 처리한다면)
그렇기에 이는 수동 빈 등록으로 명확하게 드러내는 것이 좋다.
또한, 비즈니스 로직 중 다형성(그 중 상속)을 활용한다면 명확하게 이해할 수 있게 수동 빈 등록을 사용하자
+) 아직 실무나 프로젝트 경험이 없어 크게 공감이 되지 않는다. 프로젝트 시 경험해 볼 수 있으면 좋겠다.
본 포스팅은 인프런 강의 김영한님의
[ 스프링 핵심 원리 - 기본편 ] 을 수강하며 작성한 내용입니다.