상품 주문, 주문 내역 조회, 주문 취소 기능을 구현하기 위해 엔티티에 메서드를 추가한다. 상품 주문시 상품의 재고가 감소하고, 취소 시 재고가 증가해야 한다.
주문과 주문상품의 경우 생성 시 재고를 관리해야 하고 다른 여러 엔티티들과 연관관계를 맺어줘야 한다. 이렇게 엔티티를 생성하기 복잡하다면 새롭게 생성 메서드를 만드는 것이 좋다.
주문 생성 메서드
//* 생성 메서드 *//
public static Order crateOrder(Member member, Delivery delivery, OrderItem... orderItems) {
Order order = new Order();
order.setMember(member);
order.setDelivery(delivery);
for (OrderItem orderItem : orderItems) {
order.addOrderItem(orderItem);
}
order.setStatus(OrderStatus.ORDER);
order.setOrderDate(LocalDateTime.now());
return order;
}
주문 회원, 배송정보, 주문상품의 정보를 받아서 실제 주문 엔티티를 생성한다.
주문 상품 생성 메서드
//* 생성 메서드 *//
public static OrderItem createOrderItem(Item item, int orderPrice, int count) {
OrderItem orderItem = new OrderItem();
orderItem.setItem(item);
orderItem.setOrderPrice(orderPrice);
orderItem.setCount(count);
item.removeStock(count);
return orderItem;
}
주문 상품, 가격, 수량 정보를 사용해서 주문상품 엔티티를 생성한다. 주문상품을 생성할 때 removeStock 메서드로 재고가 줄어들도록 한다.
<aside> 💡
정적 팩토리 메서드
객체를 생성하는 메소드를 만들고 static
으로 선언해 캡슐화하는 기법이다.
이 때, 다른 방법(new 등)으로 객체를 생성하지 못하게 protected 생성자를 따로 명시해주는 것이 좋다.
</aside>
주문 취소
주문을 취소할 때, 상품의 재고가 증가해야 한다.
Order.java
//* 비즈니스 로직 *//
/**
* 주문 취소
*/
public void cancel() {
if (delivery.getStatus() == DeliveryStatus.COMP) {
throw new IllegalStateException("이미 배송 완료된 상품은 취소가 불가능합니다.");
}
this.setStatus(OrderStatus.CANCEL);
for (OrderItem orderItem : orderItems) {
orderItem.cancel();
}
}
만약 이미 배송을 완료한 상품이면 주문을 취소하지 못하도록 예외를 발생시킨다. 주문 상태를 취소로 변경하고 주문상품에 주문 취소 로직을 수행한다.
OrderItem.java
//* 비즈니스 로직 *//
public void cancel() {
getItem().addStock(count);
}
addStock()으로 주문 수량(count)만큼 재고를 증가시킨다.
전체 주문 가격 조회
주문 시 사용한 전체 주문 가격을 조회한다. 전체 주문 가격을 알려면 각각의 주문상품 가격을 알아야 한다. 따라서 연관된 주문상품들의 가격을 조회해서 더한 값을 반환한다.
Order.java
/**
* 전체 주문 가격 조회
*/
public int getTotalPrice() {
int totalPrice = 0;
for (OrderItem orderItem : orderItems) {
totalPrice += orderItem.getTotalPrice();
}
return totalPrice;
}
OrderItem.java
public int getTotalPrice() {
return getOrderPrice() * getCount();
}
@Repository
@RequiredArgsConstructor
public class OrderRepository {
private final EntityManager em;
public void save(Order order) {
em.persist(order);
}
public Order findOne(Long id) {
return em.find(Order.class, id);
}
// public List<Order> findAll(OrderSearch orderSearch) {}
}