현재 AppConfig 소스코드이다.
멤버 서비서 구현체, 오더서비스 구현체가 메모리 멤버 리포지토리와 Fixed 할인 정책을 사용하는 것을 알지만 이를 한눈에 알기 어렵다
public class AppConfig {
public MemberService memberService(){
return new MemberServiceImpl(new MemoryMemberRepository());
}
public OrderService orderService(){
return new OrderServiceImpl(new MemoryMemberRepository(),new FixedDiscountPolicy());
}
}
그럼 분리를 해보자
public class AppConfig {
public MemberService memberService(){
return new MemberServiceImpl(memberRepository());
}
private MemberRepository memberRepository() {
return new MemoryMemberRepository();
}
public OrderService orderService(){
return new OrderServiceImpl(memberRepository(),discountPolicy());
}
public DiscountPolicy discountPolicy(){
return new FixedDiscountPolicy();
}
}
이렇게 분리가 되면 멤버 서비스를 멤버리포지토리 역할을 의존받아 사용하는데 멤버 리포지토리 구현체는 메모리리포지토리를 구현체를 사용한다 라는 그림이 소스코드에서도 한눈에 들어온다
AppConfig에서도 역할과 구현클래스를 한눈에 들어오게 개발하는 것이 중요하다
자 그럼 이제 할인 정책을 변경한다고 생각해보자
어디를 바꿔야 하는가❓
정답은 AppConfig에 할인 정책 구현체만 바꾸면 된다.
즉 사용하는 영역인 주문 서비스, 할인 정책 등 사용 영역은 유지한 채로 구성되는 영역이 AppConfig 만 수정하면 되는 것이다.
한 클래스는 하나의 책임만 가져야 한다.
즉 AppConfig를 통해서 관심사를 분리하고 이를 통해 책임 분리
추상화에 의존해야하지, 구체화에 의존하면 안된다. 의존성 주입은 이 원칙을 따르는 방법
기존의 구현체를 new로 할당하면서 생긴 DIP 위배를 없애고자 추상 인터페이스만 의존하도록 수정
⛔ 구현 객체가 없는 인터페이스만 있을 수 없음 그래서 AppConfig를 통한 클라이언트 코드에 의존관계 주입
소프트웨어 요소는 확장에는 열려있으나 변경에는 닫혀있어야 함
다형성을 사용하고 클라이언트가 DIP를 지킴
어플리케이션을 구성, 사용 영역으로 분리
AppConfig가 할인 정책을 바꿔도 클라이언트 코드를 수정하지 않고 Appconfig로 의존관계를 주입하는 것👍
요소를 확장해도 사용 영역은 유지