Skip to content
This repository was archived by the owner on Dec 3, 2022. It is now read-only.

[T사 과제 전형] T여행자 클럽 마일리지 서비스

Notifications You must be signed in to change notification settings

Hyune-c/traveler-mileage-service

Folders and files

NameName
Last commit message
Last commit date

Latest commit

 

History

47 Commits
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 

Repository files navigation

T여행자 클럽 마일리지 서비스

회사명 노출 및 public repository 사용을 허락받았습니다.

T사 사용자들이 장소에 리뷰를 작성할 때 포인트를 부여하고, 전체/개인에 대한 포인트 부여 히스토리와 개인별 누적포인트를 관리하고자 합니다.

# Specifications

  • 리뷰 작성 이벤트를 처리할 수 있는 API를 개발합니다.
    • 사용자는 장소마다 리뷰를 1개 작성할 수 있고, 수정 또는 삭제할 수 있습니다.
    • 리뷰 작성 보상 점수는 아래와 같습니다.
      • 내용 점수: 1자 이상 텍스트 (1점), 1장 이상 사진 첨부 (1점)
      • 보너스 점수: 특정 장소에 첫 리뷰 작성 (1점)
POST /events

{
  "type": "REVIEW",
  "action": "ADD", /* "MOD", "DELETE" */
  "reviewId": "240a0658-dc5f-4878-9381-ebb7b2667772",
  "content": "좋아요!",
  "attachedPhotoIds": [
    "e4d1a64e-a531-46de-88d0-ff0ed70c0bb8",
    "afb0cef2-851d-4a50-bb07-9cc15cbdc332"
  ],
  "userId": "3ede0ef2-92b7-4817-a5f3-0c575361f745",
  "placeId": "2e4baf1c-5acb-4efb-a1af-eddada31b00f"
}
  • 포인트 조회 API를 개발합니다.

# 실행 방법

with h2

  1. 실행
# local profile 
> ./gradlew clean bootRun --args='--spring.profiles.active=local'
  1. h2-console 접속

http://localhost:8080/h2-console

image

with mysql

  1. application.yml을 참고하여 설정 or 수정
datasource:
  driver-class-name:net.sf.log4jdbc.sql.jdbcapi.DriverSpy
  url:${DATASOURCE_URL:jdbc:log4jdbc:mysql://localhost:4306/review_schema?useSSL=false&useUnicode=true&characterEncoding=UTF-8}
  username:${DATASOURCE_USERNAME:root}
  password:${DATASOURCE_PASSWORD:password1}
  1. 실행
# default profile 
> ./gradlew clean bootRun 

Http Request Sample

https://github.com/Hyune-c/traveler-mileage-service/wiki

# 주요 기능 & 구현 의도

1. ERD 설계

image

2. 단위 테스트 & LargeTest 구현 with dynamicTest

image

3. 설계에 대한 생각

  • 레이어드 아키텍처 설계
    • web 레이어 분리
    • domain 레이어로 review와 point를 설계
    • SRP를 준수한 service 레이어 (business 레이어)
  • 포인트 적립을 Facade 패턴으로 설계 PointCreateFacade
  • JPA 기능을 한정적으로 활용한 영속성 레이어 설계
    • 성능이 필요한 기능은 querydsl 활용

3-1. Event Driven 구조의 포인트 설계

image

  • 과제 조건에는 포인트 변경의 소스가 리뷰뿐이지만, 실무라면 포인트 변경의 소스가 계속 늘어날 것입니다.
    • 포인트는 이력이 중요하며 레이스 컨디션의 주체가 적고 조회가 주가 됩니다.
    • 차후 마이크로 서비스의 분리 대상이 됩니다.
  • 따라서 history-replay 기반의 설계로 이력과 현재 포인트 조회를 가져오도록 설계 했습니다.
    • 가장 많은 요청인 현재 포인트 조회는 캐싱한 후 userId (createdBy) 기반으로 변경이 생기면 evict 합니다.
    • 단순 이력으로 설계했기에 큐를 활용하거나 비동기 로직을 통해 빠른 응답을 기대하도록 개선할 수 있습니다.
    • 마이크로 서비스로 분리된다면 CDC (Change Data Capture) 등의 기술을 활용합니다.
  • 캐시는 구현되어 있지 않습니다.

4. 지속 가능한 개발에 대한 생각

  • 레이어간/객체간 메시지 전달에 dto를 활용하고 구분된 네이밍을 정의
    • web 레이어 dto - request, response
    • service 레이어 dto - dto
  • 가독성과 안전함을 고려한 코딩
    • 함수형 프로그래밍 및 kotlin의 베스트 케이스 적용
    • google style guide, sonarlint를 활용한 컨벤션 체크
  • 가독성과 구현 의도를 알리기 위한 javadoc 작성 - public 메서드 위주
    • 실무에서도 작성하는 편이지만, 구현 의도를 알리기 위해 조금 더 자세하게 작성했습니다.

4-1. Spring Validator를 활용한 dto 검증

  • web 레이어의 bean validation만이라면 어노테이션만으로도 쉽게 됩니다.
  • 하지만 구현 요구상
    • 하나의 request에서 type에 따라 복수 종류의 요청을 처리해야하고, 비지니스 검증도 필요합니다.
    • 그렇기에 조금 과하지만 Validator를 실험적으로 활용했습니다.

4-2. 표준 예외 처리 구현 ErrorResponse

  • transactionId를 통해 요청을 추적할 수 있습니다.
    • 구현 방법에 따라 서버에서 발급한 transactionId/requestId를 사용하거나, 프론트에서 직접 발급할 수도 있습니다.
    • 이 프로젝트에서는 내부 로깅용으로 에러 추적을 위해서만 사용합니다.

image

image

About

[T사 과제 전형] T여행자 클럽 마일리지 서비스

Resources

Stars

Watchers

Forks

Releases

No releases published

Packages

No packages published

Languages