의존관계 주입
생성자 주입
- 생성자 호출 시점에 딱 1번만 호출 되는 것이 보장
- 불변, 필수 의존관계에 사용
- final 키워드!!!!
- 생성자에서 혹시라도 값이 설정되지 않는 오류를 컴파일 시점에 막아준다
- 컴파일 오류는 세상에서 가장 빠르고 좋은 오류!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
@Component
public class OrderServiceImpl implements OrderService {
private final UserRepository userRepository;
private final DiscounPolicy discountPolicy;
@Autowired
public OrderServiceImpl(UserRepository userRepository, DiscountPolicy discountPolicy) {
this.userRepository = userRepository;
this.discountPolicy = discountPolicy;
}
}
// Lombok
@Component
@RequiredArgsConstructor
public class OrderServiceImpl implements OrderService {
private final UserRepository userRepository;
private final DiscounPolicy discountPolicy;
}
수정자 주입
- 선택, 변경 가능성이 있는 의존관계에 사용
- 자바빈 프로퍼티 규약의 수정자 메서드 방식을 사용하는 방법
@Component
public class OrderServiceImpl implements OrderService {
private UserRepository userRepository;
private DiscountPolicy discountPolicy;
@Autowired
public void setUserRepository(UserRepository userRepository) {
this.userRepository = userRepository;
}
@Autowired
public void setDiscountPolicy(DiscountPolicy discountPolicy) {
this.discountPolicy = discountPolicy;
}
}
// 주입할 대상이 없어도 동작하게 하려면 @Autowired(required = false)로 지정하면 된다
필드 주입
- 코드가 간결해서 외부에서 변경이 불가능해 테스트하기 힘듬
- DI 프레임워크가 없으면 아무것도 할 수 없음
- 사용x
@Component
public class OrderServiceImpl implements OrderService {
@Autowired
private UserRepository userRepository;
@Autowired
private DiscountPolicy discountpolicy;
}
일반 메서드 주입
- 한번에 여러 필드를 주입 받을 수 있다
- 일반적으로 잘 사용 안함
@Component
public class OrderServiceImpl implements OrderService {
private UserRepository userRepository;
private DiscountPolicy discountPolicy;
@Autowired
public void init(UserRepository userRepository, DiscountPolicy discountPolicy) {
this.userRepository = userRepository;
this.discountPolicy = discountPolicy;
}
}
조회 대상 빈이 2개 이상?!
@Autowired 필드 명 매칭
// 변경전
@Autowired
private DiscountPolicy discountPolicy
// 변경 후
@Autowired
private DiscountPolicy rateDiscountPolicy
@Qualifier 사용
@Component
@Qualifier("mainDiscountPolicy")
public class RateDiscountPolicy implements DiscountPolicy{}
@Component
@Qualifier("fixDiscountPolicy")
public class FixDiscountPolicy implements DiscountPolicy{}
@Autowired
public OrderServiceImpl(UserRepository userRepository,
@Qualifier("mainDiscountPolicy") DiscountPolicy discountPolicy) {
this.userRepository = userRepository;
this.discountPolicy = discountPolicy;
}
- @Primary보다 우선순위가 높음
@Primary 사용
@Component
@Primary
public class RateDiscountPolicy implements DiscountPolicy{}
// 얘가 주입됌
@Component
public class FixDiscountPolicy implements DiscountPolicy{}
- @Qualifier보다 우선순위가 낮음
애노테이션 직접 만들기
@Target({ElementType.FIELD, ElementType.METHOD, ElementType.PARAMETER,
ElementType.TYPE, ElementType.ANNOTATION_TYPE})
@Retention(RetentionPolicy.RUNTIME)
@Documented
@Qualifier("mainDiscountPolicy")
public @interface MainDiscountPolicy {
}
@Component
@MainDiscountPolicy
public class RateDiscountPolicy implements DiscountPolicy {}
//생성자 자동 주입
@Autowired
public OrderServiceImpl(MemberRepository memberRepository,
@MainDiscountPolicy DiscountPolicy discountPolicy) {
this.memberRepository = memberRepository;
this.discountPolicy = discountPolicy;
}
자동, 수동의 올바른 실무 운영 기준
애플리케이션 두가지 로직
- 업무 로직 빈
- 웹을 지원하는 컨트롤러, 핵심 비즈니스 로직이 있는 서비스, 데이터 계층의 로직을 처리하는 리포지토리등
- 보통 비즈니스 요구사항을 개발할 때 추가되거나 변경
- 숫자도 매우 많고 한번 개발해야 하면 유사한 패턴이 있기 때문에 자동 기능을 사용하는 것이 좋음
- 기술 지원 빈
- 기술적인 문제나 공통 관심사(AOP)를 철히라 때 주로 사용됌
- 데이터베이스 연결이나, 공통 로그 처리처럼 업무 로직을 지원하기 위한 하부 기술이나 공통 기술들임
- 비교적 수가 적고 보통 애플리케이션 전반에 걸쳐서 광범위하게 영향을 미침
- 가급적 수동 빈 등록을 사용해서 명확하게 드러내는 것이 좋음
'Spring > Basic' 카테고리의 다른 글
[Basic] 빈 스코프 (0) | 2024.08.27 |
---|---|
[Basic] 빈 생명주기 콜백 (0) | 2024.08.27 |
[Basic] 컴포넌트 스캔 (0) | 2024.08.27 |
[Basic] 싱글톤 컨테이너 (0) | 2024.08.27 |
[Basic] BeanFactory / ApplicationContext (0) | 2024.08.27 |