@Autowired 빈 중복 조회

wangjh789·2022년 7월 24일
0
@Component
public class FixDiscountPolicy implements DiscountPolicy{ ... }
@Component
public class RateDiscountPolicy implements DiscountPolicy { ... }

다음과 같이 DiscountPolicy를 상속받은 2개의 클래스가 빈으로 등록되어 있다고 가정한다.
@Autowired의 기본 조회 로직은 타입에 근거하기 때문에 위와 같이 2개의 빈이 조회가 되면 에러를 발생시킨다.

필드 이름 또는 파라미터 이름 구체화

	private DiscountPolicy rateDiscountPolicy;
    
    @Autowired
	public OrderServiceImpl(..., DiscountPolicy rateDiscountPolicy){
    	...
    }

위와 같이 필드 명을 빈 이름으로 한다면 등록된 빈 중 필드 명과 같은 빈(RateDiscountPolicy)을 주입한다.

@Quilifier

@Component
@Quilifire("mainDiscountPolicy")
public class FixDiscountPolicy implements DiscountPolicy{ ... }
	private DiscountPolicy rateDiscountPolicy;
    
    @Autowired
	public OrderServiceImpl(..., 
    	@Quilifier("mainDiscountPolicy") DiscountPolicy rateDiscountPolicy){
    	...
    }

빈의 별칭을 만들고 의존성을 주입할 때 별칭을 찾아 주입한다.
하지만 주입하는 모든 코드에 별칭을 명시해야 하기 때문에 코드가 더러워진다.

@Primary

@Component
@Primary
public class FixDiscountPolicy implements DiscountPolicy{ ... }

같은 타입의 빈 중에 우선순위를 매기는 어노테이션이다.
만약 여러 개가 조회되는 경우 @Primary 어노테이션이 붙은 빈이 선택된다.
중복 빈이 2개이고, 명확한 우선순위가 있는 경우 편리하게 사용할 수 있다.

@Quilifier vs @Primary

이 경우 더 구체적인 별칭을 명시한 @Quilifier를 가진 빈이 선택된다.

의도적으로 여러 개의 빈을 받아야 하는 경우

할인 정책에 있어서 동적으로 런타임때 필요한 정책을 사용해야 한다는 상황일 때

class DiscountService{
        private final Map<String, DiscountPolicy> policyMap;
        private final List<DiscountPolicy> discountPolicies;

        @Autowired
        public DiscountService(Map<String, DiscountPolicy> policyMap, List<DiscountPolicy> discountPolicies) {
            this.policyMap = policyMap;
            this.discountPolicies = discountPolicies;
        }

        public int discount(Member member, int price, String discountCode) {
            DiscountPolicy discountPolicy = policyMap.get(discountCode);
            return discountPolicy.discount(member, price);
        }
    }

생성자 컬렉션 파라미터 자동주입을 사용한다면
Map의 경우{fixDiscountPolicy=hello.core.discount.FixDiscountPolicy@73302995, rateDiscountPolicy=hello.core.discount.RateDiscountPolicy@1838ccb8} ,
List의 경우
[hello.core.discount.FixDiscountPolicy@73302995, hello.core.discount.RateDiscountPolicy@1838ccb8]
가 주입된다.
편하게 전략패턴을 구현할 수 있다.

profile
기록

0개의 댓글