반응형
Spring 에서는 @Autowired를 통해서 혹은 유일한 생성자로 의존성 주입을 할 수 있습니다.
@Autowired는 기본적으로 타입으로 빈을 조회하는데 같은 타입의 빈이 2개 이상 컨테이너에 등록되어있을 때는 어떻게 할까요?
코드로 보자면 아래와 같은 상황입니다.
@Component
public class FixDiscountPolicy implements DiscountPolicy {
}
@Component
public class RateDiscountPolicy implements DiscountPolicy {
}
@Component
public class OrderServiceImpl implements OrderService {
private final DiscountPolicy discountPolicy;
public OrderServiceImpl(DiscountPolicy discountPolicy) {
this.discountPolicy = discountPolicy;
}
}
이런 상황에서는 NoUniqueBeanDefinitionException 이 터집니다..
nested exception is org.springframework.beans.factory.NoUniqueBeanDefinitionException: No qualifying bean of type 'hello.core.discount.DiscountPolicy' available: expected single matching bean but found 2: fixDiscountPolicy,rateDiscountPolicy
이 상황에서는 3가지 해결방법이 있습니다.
1. @Autowired 필드명으로 매칭
2. @Qualifier 끼리 매칭
3. @Primary 사용
@Autowired 필드명으로 매칭하는건 코드를 아래와 같이 변경하면 되는데, 이것은 사용할 빈이 바뀌면 다시 수정해야 하기 때문에 유지보수 측면에서 좋지않습니다.
@Component
public class OrderServiceImpl implements OrderService {
private final DiscountPolicy rateDiscountPolicy;
}
@Qualifier 사용도 역시 의존성을 제공하는 측과 제공받는 측 모두 수정이 일어납니다.
대체적으로 @Primary 사용이 가장 좋겠습니다.
아래와 같이 우선적으로 조회하고자 하는 Component에 @Primary annotation을 마킹합니다.
@Component
@Primary
public class RateDiscountPolicy implements DiscountPolicy {
}
그러면, 같은 타입의 빈들이 모두 필요할 때는 어떻게 하면 될까요?
이때는 Collections로 가져올 수 있습니다
class DiscountService {
private final Map<String, DiscountPolicy> discountPolicyMap;
private final List<DiscountPolicy> discountPolicies;
@Autowired
public DiscountService(Map<String, DiscountPolicy> discountPolicyMap, List<DiscountPolicy> discountPolicies) {
this.discountPolicyMap = discountPolicyMap;
this.discountPolicies = discountPolicies;
}
}
타입이 같은 상황, 지금 이 포스팅에서는 같은 인터페이스를 구현하고 그 인터페이스 타입으로 의존성 주입을 시도하는 상황입니다.
이런 상황에서 Bean을 특정하는 방법과 그 Bean들을 모두 가져오는 방법에 대해서 알아봤습니다!!
반응형
'소프트웨어' 카테고리의 다른 글
DriverManager는 어떻게 Driver를 찾을까..? (0) | 2022.05.25 |
---|---|
정적 팩터리 메서드는 생성자보다 좋을까? (0) | 2021.09.15 |
406 Not Acceptable HttpMediaTypeNotAcceptableException (1) | 2021.08.21 |
Spring AOP (Aspect Oriented Programming) (0) | 2021.08.14 |
Checked vs Unchecked Exception (0) | 2021.08.10 |