DI(의존성 주입)의 필요성
아래와 같은 전통적인 자바 코드는 구현체가 변경될 경우 코드 수정이 필수적이다. 이는 역할과 구현이 완전하게 분리되어 있지 않은 것을 뜻하며, 객체지향 설계의 5원칙(SOLID) 중 OCP/DIP 원칙에 어긋난다.
public class OrderServiceImpl implements OrderService {
private final MemberRepository memberRepository = new MemoryMemberRepository();
private final DiscountPolicy discountPolicy = new FixDiscountPolicy();
@Override
public Order createOrder(Long memberId, String itemName, int itemPrice) {
Member member = memberRepository.findById(memberId);
int discountPrice = discountPolicy.discount(member, itemPrice);
return new Order(memberId, itemName, itemPrice, discountPrice);
}
}
역할과 구현을 연결해주는 별도 Config 클래스를 작성하여 구현을 역할에 강제로 주입해줄 수 있다.
public class AppConfig {
public MemberService memberService() {
return new MemberServiceImpl(memberRepository());
}
public OrderService orderService() {
return new OrderServiceImpl(
memberRepository(),
discountPolicy());
}
public MemberRepository memberRepository() {
return new MemoryMemberRepository();
}
public DiscountPolicy discountPolicy() {
return new FixDiscountPolicy();
}
}
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;
}
@Override
public Order createOrder(Long memberId, String itemName, int itemPrice) {
Member member = memberRepository.findById(memberId);
int discountPrice = discountPolicy.discount(member, itemPrice);
return new Order(memberId, itemName, itemPrice, discountPrice);
}
}
AppConfig를 통해 역할과 구현이 완벽하게 분리되었다. 그러나 Config클래스들을 일일이 작성/관리하는 것도 쉬운 일은 아니다. 스프링을 통해 AppConfig를 다시 작성해보자.
댓글남기기