역할과 구현에 따라 코드를 분리하여 작성한다.
크게 주문서비스 역할, 회원 저장소 역할, 할인 정책 역할로 구분되어 있으며 역할에 따라 구현 클래스를 만드는 방식으로 설계되어 있다. 이렇게 코드를 작성하면 변경과 확장에 유리하다.
interface를 활용하여 코드를 작성하면 할인정책이나 DB를 변경해야할 경우에도 비교적 수월하게 변경할 수 있다는 장점이 있다.
할인정책 인터페이스를 만들고 인터페이스를 구현하는 정액할인정책 클래스를 만들어준다.
이렇게 코드를 만들면 향후 다른 할인 정책으로 변경할 때 구현 클래스만 따로 하나 더 만들거나 수정하면 된다.
//할인정책 인터페이스
public interface DiscountPolicy {
int discount(Member member, int price);
}
//할인정책 인터페이스를 구현하는 FixDiscountPolicy 클래스
public class FixDiscountPolicy implements DiscountPolicy{
private int discountFixAmount = 1000;
//1000원 할인
@Override
public int discount(Member member, int price) {
if(member.getGrade() == Grade.VIP){
return discountFixAmount;
} else {
return 0;
}
}
}
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);
}
}
OrderServiceImpl에서는 member 객체만 전달하면 discountPolicy 클래스에서 가격을 계산하는 로직을 전부 처리하기 때문에 향후 할인 관련한 로직을 변경해야 할 경우 discountPolicy 클래스만 수정하면 되기 때문에 단일 책임의 원칙을 잘 지킨 코드다.
이 글은 김영한님의 스프링 핵심 원리 강의를 듣고 정리한 내용입니다.