
토이 프로젝트 개요
다수 서버 환경에서 안정적으로 동작하는 커피샵 주문 시스템 구현해보기
- 커피 메뉴 목록 조회
- 포인트 충전, 결제는 오직 포인트로만
- 커피 주문
- 주문 후 주문 정보를 Mock API로 전송해보기
- 주문 횟수에 따른 인기 메뉴 조회의 정확성을 보장할 수 있어야함
- 인기 메뉴 조회 (7일치 Top 3)
ERD

진행 경과
설계와 로직 작성 과정, 트러블슈팅
UUID v7 사용
- 식별자를 AUTO_INCREMENT 를 사용하면 다중 DB 환경에서 키 중복 가능성이 농후함
- 단순 UUID 를 사용하기엔 추후 인덱스나 아이디를 사용한 정렬에 문제가 있음
- v7 은 시간 정렬이 더해진 UUID 이므로 활용해도 무방하다 판단하여 적용
커피 메뉴 조회
- 커피 메뉴를 조회할 때 캐싱을 효율적으로 사용하기 위해 수량 정보를 따로 담도록 엔티티를 분리
- 인기 메뉴 조회의 정확성을 보장하기 위해 일별 주문 횟수를 보관하는 엔티티를 따로 마련
포인트 충전, 사용시 로그 마련 , 인기 메뉴 조회 정확성을 위한 주문횟수 엔티티 데이터 생성 , 주문 후 주문 정보를 Mock API로 전송해보기
- Kafka 이벤트 발행 사용 적용과 문제점들 발생
- 오류로 트랜잭션이 롤백되었어도 메세지는 발행될 수 있음 그렇게 발행되어 진행되버리면 의미를 잃어버린 데이터가 생김
- ApplicationEventPublisher 를 통해 @TransactionEventListner(AFTER_COMMIT) 처리
- 커밋이 마쳐지면 이벤트 발행되도록 적용
분산 락 적용시 REQUIRES_NEW 적용에 따른 문제점 해결
- 락 해제 전 비즈니스 로직이 커밋되도록 보장하도록 위한 조치
- 허나 비즈니스 로직에 적용된 트랜잭션과 중첩이 되면 이중 커넥션 점유 문제 생김 클래스 내에서 따로 메서드 분리를 해서 사용하면 Self-Invocation 문제 발생
- 단순히 트랜잭션을 없애서 해결하는 것도 가능하지만 흐름 제어 및 로직이 겹쳐 비대해진 서비스 클래스를 따로 역할 분리할 겸 Facade 패턴 적용
< Redisson 을 통한 분산 락 구현과 이에 사용된 REQUIRES_NEW 전파 > < 분산 락이 적용된 주문시 수량 감소 부분 > < Facade 적용 - 조회, 검증 후 주문 진행에 따른 재고, 포인트 차감 흐름 제어, 마지막 주문 저장 처리 > < 기존 Service 는 데이터 저장의 역할을 가져감 + Kafka 메세지 발행 진행 > < 주문 후 정상적으로 발행되는 Kafka 이벤트>
인기 메뉴 조회 (7일치 Top3)
- 정확성 보장이 관건이므로
menu_order_count엔티티를 따로 구성하여 주문시 메뉴 아이디 별 주문 횟수가 일자별로 저장되도록 처리함
- Redis ZSet 을 이용하여 인기 메뉴 캐싱 처리 MISS 의 경우를 대비한 별도 엔티티에서도 처리할 수 있도록 마련
< 주문 시 ZSet 점수 증가를 위한 메서드 - 주문 시 커밋이 완료되면 이벤트 발행을 통해 Kafak 메세지 발행되어 주문 횟수 증가 >
Share article









