public interface DiscountPolicy {
int discount(Member member, int price);
}
위와같은 할인정책 인터페이스와
public class RateDiscountPolicy implements DiscountPolicy{
...
public class FixDiscountPolicy implements DiscountPolicy{
...
할인정책 인터페이스의 구현체가 있다.
@Component
public class OrderServiceImpl implements OrderService{
private final MemberRepository memberRepository;
private final DiscountPolicy discountPolicy;
public OrderServiceImpl(MemberRepository memberRepository, DiscountPolicy discountPolicy) {
this.memberRepository = memberRepository;
this.discountPolicy = discountPolicy;
}
주문 서비스의 구현체 생성자에 인터페이스 DiscountPolicy를 쓴다면?
public class AutoAppConfigTest {
@Test
void basicScan(){
AnnotationConfigApplicationContext ac = new AnnotationConfigApplicationContext(AutoAppConfig.class);
...
}
}
AnnotationConfigApplicationContext
는 컴포넌트스캔을 할 때RateDiscountPolicy
와 FixDiscountPolicy
중에 누구를 불러와야하는지 몰라서 UnsatisfiedDependencyException
를 띄운다. 이를 해결하기위해서는 DI할때 처리를 해야겠죠?
이제 처리하는 3가지 방법에 대해 알아보자!
@Autowired
public OrderServiceImpl(MemberRepository memberRepository, DiscountPolicy discountPolicy) {
this.memberRepository = memberRepository;
this.discountPolicy = discountPolicy;
}
필드주입을 하는 상황이면 필드명에 이름을 rateDiscountPolicy로 명시해서
@Autowired
public OrderServiceImpl(MemberRepository memberRepository, DiscountPolicy rateDiscountPolicy) {
this.memberRepository = memberRepository;
this.discountPolicy = rateDiscountPolicy;
}
이렇게 넣어주기만해도 정상작동한다.
어노테이션끼리 매칭
단점은 주입 받을 때 모든 코드에 붙여야함
@Component
@Qualifier("RateDiscountPolicy")
public class RateDiscountPolicy implements DiscountPolicy{
...
@Component
public class OrderServiceImpl implements OrderService{
private final MemberRepository memberRepository;
private final DiscountPolicy discountPolicy;
public OrderServiceImpl(MemberRepository memberRepository, @Qualifier("RateDiscountPolicy") DiscountPolicy discountPolicy) {
this.memberRepository = memberRepository;
this.discountPolicy = discountPolicy;
}
...
@Component
@Primary
public class RateDiscountPolicy implements DiscountPolicy {
...
}
@Component
public class FixDiscountPolicy implements DiscountPolicy {
...
}
이렇게 @Primary
를 한곳에 붙여넣으면 우선순위가 최상위로 잡힘 근데 @Quilifier랑 같이쓰면 얘가 우선이됨. 스프링은 대부분 수동>자동 이라고 알아두면 편함 두개 다 @Primary
붙여보니까 똑같이 UnsatisfiedDependencyException
오류가 뜨더라구요 ㅎg 하나만 붙여둬야하는듯?
음.. 아직도 좀 불편한데..? 그리고 둘 이상의 빈중에 하나만 쓰는 경우말고 다 쓰는 방법도 있을텐데 진도를 더 빼다보면 나오겠죠?