@Autowired는 타입으로 조회하기 때문에 선택되는 빈이 한 개가 아닌 경우 NoUiqueBeanDefinitionException이 발생한다. 이를 다음의 3가지 방법으로 해결할 수 있다.
1. @Autowired 사용 시 필드 명으로 매칭되게 하기
@Autowired는 일차적으로 타입으로 매칭을 시도하지만 같은 타입의 빈이 있는 경우 필드 이름 및 파라미터 이름으로 빈을 매칭한다.
public class OrderServiceImpl implements OrderService {
@Autowired
private PointPolicy pointPolicy;
...
}
@Component
public class FixPointPolicy implements PointPolicy {...}
@Component
public class RatePointPolicy implements PointPolicy {...}
따라서 위와 같이 작성된 코드의 경우 PointPolicy를 구현하는 클래스는 FixPointPolicy와 RatePointPolicy가 존재하고, 둘 다 @Component
로 등록되었다. 따라서 위의 코드를 그대로 사용하면 NoUiqueBeanDefinitionException
이 발생한다.
public class OrderServiceImpl implements OrderService {
@Autowired
private PointPolicy ratePointPolicy;
...
}
이 경우 위와 같이 코드를 수정하면 @Autowired
의 필드 명이 ratePointPolicy이므로 RatePointPolicy 클래스가 정상적으로 빈으로 매칭된다.
2. @Qualifier 사용하기
@Qualifier
로 추가 구분자를 지정해 의존 관계 주입 시에 추가적인 옵션을 제공한다.
@Component
로 등록 시에 @Qualifier
를 사용해 옵션을 지정한다.
@Component
@Qualifier("fixPointPolicy")
public class FixPointPolicy implements PointPolicy {...}
@Component
@Qualifier("mainDiscountPolicy")
public class RatePointPolicy implements PointPolicy {...}
@Autowired
로 의존 관계 주입 시에 @Qualifier
로 호출할 빈을 설정한다.
@Autowired
public OrderServiceImpl(MemberRepository memberRepository,
@Qualifier("mainDiscountPolicy") PointPolicy pointPolicy) {
this.memberRepository = memberRepository;
this.pointPolicy = pointPolicy;
}
3. @Primary로 우선 순위를 지정하기
@Component
로 빈 등록 시에 @Primary
를 붙이면 @Autowired
로 여러 빈이 매칭된 경우 @Primary
가 붙은 빈이 우선권을 가지게 되고, 매칭된다.
@Component
public class FixPointPolicy implements PointPolicy {...}
@Component
@Primary
public class RatePointPolicy implements PointPolicy {...}
'back-end > spring' 카테고리의 다른 글
spring/ 빈 스코프 (0) | 2022.06.21 |
---|---|
spring/ 빈 생명주기 콜백 (0) | 2022.06.21 |
spring/ 롬복lombok 사용하기 (0) | 2022.06.21 |
spring/ 의존 관계 자동 주입 - 생성자 주입을 사용하자 (0) | 2022.06.20 |
spring/ 컴포넌트 스캔 (0) | 2022.06.20 |