
회원은 상푼을 주문 가능
회원 등급에 따라 할인 정책을 적용 가능
할인 정책은 모든 vip는 1000원을 할인해주는 고정 금액 할인을 적용(나중에 변경 가능)
할인 정책은 변경 가능성이 높다. 할인을 적용하지 않을 수도 있다.(미확정)
주문 도메인 협력, 역할, 책임

주문 도메인 전체

역할과 구현을 분리 자유롭게 구현 객체를 조립할 수 있도록 설계하였다.
회원 저장소와 할인 정책을 유연하게 변경할 수 있다.
주문 도메인 클래스 다이어그램

주문 도메인 객체 다이어그램1

주문 도메인 객체 다이어그램2

역할들의 협력 관계를 그대로 재사용할 수 있다.
discount, order 폴더 생성
discount
order
할인정책을 정의하는 인터페이스이다.
위의 다이어그램을 참고하면 정액할인정책과 정률할인정책이 존재할 수 있다.
하지만 우리는 주문 객체 도메인1 대로 개발할 것이므로 정액할인정책만 사용하겠다.
public interface DiscountPolicy {
/**
* @return 할인 대상 금액
*/
int discount(Member member, int price);
}
할인정책을 구현하는 클래스로, 정액할인정책을 구현할 것이다.
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 Order {
private Long memberId;
private String itemName;
private int itemPrice;
private int discountPrice;
public Order(Long memberId, String itemName, int itemPrice, int discountPrice) {
this.memberId = memberId;
this.itemName = itemName;
this.itemPrice = itemPrice;
this.discountPrice = discountPrice;
}
public int calculatorPrice(){
return itemPrice - discountPrice;
}
public Long getMemberId() {
return memberId;
}
public void setMemberId(Long memberId) {
this.memberId = memberId;
}
public String getItemName() {
return itemName;
}
public void setItemName(String itemName) {
this.itemName = itemName;
}
public int getItemPrice() {
return itemPrice;
}
public void setItemPrice(int itemPrice) {
this.itemPrice = itemPrice;
}
public int getDiscountPrice() {
return discountPrice;
}
public void setDiscountPrice(int discountPrice) {
this.discountPrice = discountPrice;
}
@Override
public String toString() {
return "Order{" +
"memberId=" + memberId +
", itemName='" + itemName + '\'' +
", itemPrice=" + itemPrice +
", discountPrice=" + discountPrice +
'}';
}
}
주문서비스 메서드를 생성하는 인터페이스이다.
주문서비스는 주문을 생성한다.
public interface OrderService {
Order createOrder(Long memberId, String itemName, int itemPrice);
}
주문을 생성하는 메서드를 구현하는 인터페이스
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);
}
}
실행
public class OrderApp {
public static void main(String[] args) {
MemberService memberService = new MemberServiceImpl();
OrderService orderService = new OrderServiceImpl();
Long memberId = 1L;
Member member = new Member(memberId, "memberA", Grade.VIP);
memberService.join(member);
Order order = orderService.createOrder(memberId, "itemA", 10000);
System.out.println("order=" + order);
System.out.println("order.calculate= "+order.calculatorPrice());
}
}
실행시켜보면 주문 조회가 가능하고 할인이 적용된 금액을 확인할 수 있다.
테스트
public class OrderServiceTest {
MemberService memberService = new MemberServiceImpl();
OrderService orderService = new OrderServiceImpl();
@Test
void createOrder(){
Long memberId = 1L;
Member member = new Member(memberId, "memberA", Grade.VIP);
memberService.join(member);
Order order = orderService.createOrder(memberId, "itemA", 10000);
Assertions.assertThat(order.getDiscountPrice()).isEqualTo(1000);
}
}
테스트코드도 만들어서 실행시켜보자.