스프링에서 자동 의존성 주입인 @Autowired를 사용할 때 Bean이 여러 개 존재하면 어떤 빈을 주입해야 할 지 모호해서 오류가 발생할 수 있다.
세 가지 방법이 존재하는데 @Autowired 필드, @Qualifier, @Primary 같은 기능들이 있다.
- @Primary는 기본적으로 우선순위를 정하는 방식으로 널리 사용됨.
- @Qualifier는 특정한 빈을 명확하게 지정해야 할 때 자주 사용됨.
- @Autowired 필드 명 매칭은 자동으로 이름을 맞춰줄 때 활용됨.
자동 주입 충돌 방지와 명확한 의존 관계 설정을 위해서 실무에서 많이 활용되므로 간단하게 공부하는 김에 코드를 통해 예시를 들어보겠다.
@Autowired 필드 명 매칭
자동 주입할 때 필드 명과 빈 이름이 같다면 해당 빈을 자동으로 매칭한다.
@Component
public class Apple implements Fruit {
@Override
public String getName() {
return "🍎 Apple";
}
}
@Component
public class Banana implements Fruit {
@Override
public String getName() {
return "🍌 Banana";
}
}
@Component
public class FruitService {
@Autowired
private Fruit banana; // 필드 명을 `banana`로 설정 → Banana 빈이 자동 주입됨
public void printFruit() {
System.out.println("Selected Fruit: " + banana.getName());
}
}
@Autowired는 기본적으로 타입 매칭을 먼저 시도하지만 빈이 여러 개라면 필드 명과 같은 빈을 찾아서 매칭한다.
실행 결과
Selected Fruit: 🍌 Banana
@Qualifier로 특정 빈 지정
같은 타입의 빈이 여러 개 있을 때, 특정 빈을 명확하게 지정할 수 있는 방법이 있다.
@Component
@Qualifier("sweetOrange") // 구분자 추가
public class Orange implements Fruit {
@Override
public String getName() {
return "🍊 Sweet Orange";
}
}
@Component
@Qualifier("sourOrange") // 구분자 추가
public class SourOrange implements Fruit {
@Override
public String getName() {
return "🍊 Sour Orange";
}
}
@Component
public class FruitService {
private final Fruit orange;
@Autowired
public FruitService(@Qualifier("sweetOrange") Fruit orange) { // @Qualifier를 통해 특정 빈 선택
this.orange = orange;
}
public void printFruit() {
System.out.println("Selected Fruit: " + orange.getName());
}
}
@Qualifier("sweetOrange")로 인해 Sweet Orange 빈이 선택된다.
구체적인 빈을 주입해야 할 때 @Qualifier를 사용하면 명확한 해결이 가능하다.
실행 결과
Selected Fruit: 🍊 Sweet Orange
@Primary를 사용한 기본 빈 설정
간단하게 구체적인 설정 없이 여러 개의 같은 타입 빈이 있을 때 기본 빈을 정할 수 있는 방법이 있다.
@Component
@Primary // 기본 빈으로 설정됨
public class Watermelon implements Fruit {
@Override
public String getName() {
return "🍉 Watermelon";
}
}
@Component
public class Grape implements Fruit {
@Override
public String getName() {
return "🍇 Grape";
}
}
@Component
public class FruitService {
private final Fruit fruit;
@Autowired
public FruitService(Fruit fruit) { // @Primary가 적용된 Watermelon이 기본적으로 주입됨
this.fruit = fruit;
}
public void printFruit() {
System.out.println("Selected Fruit: " + fruit.getName());
}
}
@Primary가 붙은 Watermelon 빈이 자동 설정된다.
특별한 지정 없이 기본적으로 사용될 빈을 정할 때 유용하다.
실행 결과
Selected Fruit: 🍉 Watermelon
@Primary vs @Qualifier
기본적으론 @Qualifier가 둘 다 사용됐을 땐 우선된다.
사용 목적에 따라 둘 다 다르게 사용되는 중요한 방법이다.
@Primary는 자주 쓰는 빈을 기본 빈으로 설정할 때 사용하고 @Qualifier는 특정 빈을 선택해야 할 때만 사용하면 코드가 깔끔해진다.
결론:
✅ @Autowired 필드 명 매칭 → 필드 명과 동일한 빈이 자동으로 주입됨
✅ @Qualifier → 여러 빈 중 특정 빈을 명확히 선택할 때 사용
✅ @Primary → 기본적으로 사용할 빈을 정할 때 사용
'Backend > Spring Boot' 카테고리의 다른 글
빈이 존재하는 범위를 이해하자 (0) | 2025.02.19 |
---|---|
스프링 빈의 생명주기 콜백에 대해서 (0) | 2025.02.12 |
@Configuration 없이 @Bean만 사용하면? (0) | 2025.02.09 |
@Controller와 @RestController 차이 (1) | 2025.02.04 |
싱글톤 패턴 (0) | 2024.10.14 |