Skip to content

Commit

Permalink
버전 1.0 �병합 (#159)
Browse files Browse the repository at this point in the history
* 공통모듈에 공통객체 정의 (#7)

* chore(#6): spring data jpa 의존성 추가

* feat(#6): 공통모듈에 공통응답 객체들 추가
- 공통 커스텀 예외인 BusinessException
- 공통 응답인 ApiResponse
- Audit 속성을 정의한 BaseEntity

* 게이트웨이 모듈 생성 및 환경 설정 (#9)

* chore(#3): Gateway 모듈 생성

* chore(#3): Gateway 모듈 환경 설정
- auth, user path 추가
- eureka client 연결

* 결제 모듈 생성 (#14)

* 상품관련 모듈 추가 및 라우팅 설정  (#16)

* feat(#5): product 모듈 추가
- local 프로파일 관련 yml 설정

* feat(#5): product_dto 모듈 추가

* chore(#5): service에 product, product_dto 등록

* chore(#5): gateway에 product관련 라우팅 정보 등록

* Order, Notification 모듈 생성 (#18)

* feat(#5): 주문, 알림 모듈 생성

- 주문 모듈 생성
- 주문 개발환경 세팅
- 알림 모듈 생성
- 알림 개발환경 세팅

* Auth 모듈 생성 및 Gateway 필요없는 폴더 삭제 (#19)

* remove(#17): Gateway gradle 삭제
* chore(#17): Auth 모듈 생성

* feat(#25): 주문 DTO 모듈 생성 (#27)

* 회원가입 기능 추가 (#26)

* remove(#10): 사용하지 않는 파일 제거
- domain/.../application.properties
- user/dto

* feat(#10): 회원가입 기능 추가
- 테스트 코드 작성(서비스, api)

* refactor(#10): 유저 에러 코드 수정
- status 데이터 타입 변경 (String -> HttpStatus)

* feat(#29): gradle wrapper 오류 문제 해결 (#31)

* 슬랙 모듈 생성 (#32)

* feat(#30): 슬랙 모듈 생성

* 로그인 시 필요한 UserDto 모듈 구성 (#33)

- 사용하지 않는 resources, test 폴더 삭제

* 사용자 이름으로 조회 기능 구현 및 user.dto 수정 (#37)

* feat(#11): 로그인 시 필요한 사용자 이름으로 가져오는 API 구현
- 테스트 코드 작성

* fix(#11): user.dto 수정
- user.dto에 들어가는 클래스는 다른 서비스에서 사용해야함으로 static으로 만들면 안됨
- dto 수정에 따른 소스 코드 수정

* 상품 추가 API 구현  (#34)

* chore(#23): docker-compose.yml 등록
- kafka(zoookeeper, kafka-ui 포함), elastic-search(kibana), casandra(product에서만 쓰이는 nosqlDB) 추가

* chore(#23): product server 모듈명 변경으로 인한 설정 수정

* chore(#23): cassandra 의존성 추가 및 설정

* chore(#23): cassandra repository 추가 및 audit 설정

* feat(#23): 상품 추가 API 구현
- validation 의존성 추가
- discountPercent에 따라 discountPrice 적용
- createdAt 초기화를 위해 isNew 속성 추가

* chore(#23): Elastic Search 추가

* feat(#23): 상품등록시 elastic search에 비동기로 저장하는 로직 추가
- 검색엔진 저장용 dto인 ProductSearchDto 생성
- async 사용

* 슬랙 전송 api 생성 (#46)

* feat(#30): 슬랙 모듈 생성

* feat(#30): Message entity 생성

* feat(#30): Message Exception 생성

exception 발생시 에러 로깅

* feat(#30): slack message 전송기능 생성

* refactor(#30): message entity 수정

- user Id 제거
- base entity 상속 제거 및 send At 추가

* 장바구니 상품 개수 수정, 상품 삭제, 전체삭제 API 구현 (#43)

- 장바구니 상품 추가 API 구현 및 http 테스트 작성
- 장바구니 조회 API 구현 및 http 테스트 작성
- 장바구니 상품 개수 추가 API 구현 및 http 테스트 작성
- 장바구니 상품 삭제 API 구현 및 http 테스트 작성
- 장바구니 전체삭제 API 구현 및 http 테스트 작성
- Cart 커스텀 예외 추가 및 설정
- 장바구니 예외 핸들러 구현
- request dto 유효성 검증 추가

* 상품 수정/삭제/상태변경 API 구현 (#49)

* chore(#47): product 서버 예외 관련 클래스들 정의

* feat(#47): 상품 수정 API 구현
- spring data 카산드라는 변경감지 예외가 없어 save로 저장
- elastic search도 성능문제방지를 위해 덮어쓰기 방식으로 저장

* fix(#47): 상품조회시 isDelete가 false인것만 조회되도록 수정
- 카산드라에 수동으로 isDeleted 컬럼에 인덱스를 설정해야함

* feat(#47): 상품 삭제, 상태변경  API 구현
- DB는 soft delete처리로 isDelete값만 변경, 검색엔진은 실제로 삭제처리
- 상태변경 컬럼인 soldout 컬럼 추가

* 로그인 기능 구현 (#48)

* chore(#11): 로그인 시 필요한 UserDto 모듈 구성
- 사용하지 않는 resources, test 폴더 삭제

* feat(#11): 로그인 시 필요한 사용자 이름으로 가져오는 API 구현
- 테스트 코드 작성

* feat(#11): 로그인 기능 구현
- 테스트 코드 및 API 테스트 작성

* 장바구니 트랜잭션 적용 및 만료기한 설정 (#53)

* feat(#52): 장바구니 만료기한 설정 구현

* feat(#52): 장바구니 트랜잭션 설정 추가

* CI - build 구성 (#20)

* chore(#12): CI 구성
- dev branch에 push or PR를 날리면 build 되는지 확인 후에 merge한다.
- build.gradle이 포함된 모든 디렉토리를 돌며 build 진행
- 루트 폴더에 있는 gradlew만 사용
- GNU Parallel을 사용하여 병렬로 빌드
- service 폴더 안에서만 build.gradle을 찾도록 수정
- 각 모듈마다 테스트는 진행 X

* CI 파이프 라인 수정 (#61)

** docs(#12): CI 파이프 라인 수정
- dev에 PR 올릴 때만 build
- google-java-format 추가

* docs: [CI] dev에 push 시에도 검사하도록 수정

* Auth 모듈에서 토큰 검증 (#54)

* chore(#15): 인증 작업을 위한 auth.dto 모듈 추가
- 인증 작업 시 gateway 모듈에서 사용

* remove(#15): gateway 모듈에서 필요없는 파일 제거

* feat(#15): Auth 앱에서 토큰 검증
- 단위 테스트 작성
- 기존 JwtHandler 삭제

* user, auth  dto 수정 (#63)

* fix(#62): auth.dto > auth.auth_dto 로 수정

* fix(#62): user.dto > user.user_dto 로 수정

* remove(#62): gradle 폴더 제거

* slack dto 모듈 생성 (#56)

* feat(#30): 슬랙 모듈 생성

* feat(#30): Message entity 생성

* feat(#30): Message Exception 생성

* feat(#30): slack message 전송기능 생성

* refactor(#30): message entity 수정

* feat(#30): slack dto 모듈 생성

* 인증/인가 추가 (#64)

* feat(#15): gateway 모듈에서 검증된 토큰 헤더에 추가 후 요청 전달
* feat(#15): User 모듈에 spring security 및 커스텀 필터(헤더 파싱) 추가

* 결제 기본 API (#57)

* feat(#4): 결제 모듈 생성

* rename(#4): 폴더 구조 수정

com.sparta.payment.server -> com.sparta.payment

* feat(#4): 결제, 결제내역 Entity 생성

* rename(#4): entity 위치 변경

* feat(#4): 결제 생성 API

- toss payments 연결

* feat(#4): 결제 DB 저장

- user Id String -> Long 변경
- base entity 상속 x -> created_At 추가

* feat(#4): 예외처리 추가

* feat(#4): 결제 생성 시 history 내역 저장 추가

* feat(#4): 결제 승인 요청 로직 생성

* feat(#4): 결제 취소 로직 생성

* feat(#4): 결제 승인 추가

- 결제 완료시 주문 feign api 호출해서  주문 완료 시킬 수 있도록 구현해야 함

* feat(#4): order Id로 결제 조회

* refactor(#4): dto 구조 변경

* feat(#4): payment 조회 생성

payment 단건 조회
payment history 조회
payment 전체 조회
order Id로 payment 조회

* CI pipeline 수정 (#66)

* fix(#65): CI pipeline 수정
- on에서 push branch dev 제거
- 각 모듈을 순차적으로 빌드
- Google Java Format 추가

* fix: Google Java Format 제거
- 현재 IDE에서 사용하고 있는 포맷과 맞지 않음. 맞출려면 스크립트로 맞춰야해서 제거

* 상품 조회 API 구현 및 상품 컬럼 추가 (#67)

* feat(#59): 단일상품조회 API 구현

* feat(#59): 주문시 상품정보를 가져오는 내부 API 정의
- 요청에서 삭제된 상품정보는 아예 넘어오지 않아서 없는 경우 not found exception

* feat(#59): 상품엔티티에 필터링과 관련된 컬럼 추가
- 상품 조회시 필요한 필터링 요소로 브랜드이름, 메인컬러, 사이즈, 태그 추가 및 쿠폰여부 제거
- 태그로 "COUPON", "EXPRESS_DELIVERY", "FREE_SHIPPING", "DISCOUNT", "NEW", "1+1", "RECOMMEND"가 추가될 수 있음
- 상품 조회시 필요한 정렬 요소로 리뷰카운트, 세일즈카운트 속성 추가 나중에 리뷰추가나 주문시 해당 count 증가가 필요
- 엔티티 속성추가로 변동되는 모든 dto, mapper 요소를 함께 수정

* slack feign 연결 (#68)

* feat(#4): 결제 모듈 생성

* rename(#4): 폴더 구조 수정

com.sparta.payment.server -> com.sparta.payment

* feat(#4): 결제, 결제내역 Entity 생성

* rename(#4): entity 위치 변경

* feat(#4): 결제 생성 API

- toss payments 연결

* feat(#4): 결제 DB 저장

- user Id String -> Long 변경
- base entity 상속 x -> created_At 추가

* feat(#4): 예외처리 추가

* feat(#4): 결제 생성 시 history 내역 저장 추가

* feat(#4): 결제 승인 요청 로직 생성

* feat(#4): 결제 취소 로직 생성

* feat(#4): 결제 승인 추가

- 결제 완료시 주문 feign api 호출해서  주문 완료 시킬 수 있도록 구현해야 함

* feat(#4): order Id로 결제 조회

* refactor(#4): dto 구조 변경

* feat(#4): payment 조회 생성

payment 단건 조회
payment history 조회
payment 전체 조회
order Id로 payment 조회

* feat(#4): message feign client 연결

- 결제 생성시 유저에게 해당 결제 url 전송

* payment dto 모듈 생성  (#70)

* feat(#4): 결제 모듈 생성

* rename(#4): 폴더 구조 수정

* feat(#4): 결제, 결제내역 Entity 생성

* rename(#4): entity 위치 변경

* feat(#4): 결제 생성 API

- toss payments 연결

* feat(#4): 결제 DB 저장

* feat(#4): 예외처리 추가

* feat(#4): 결제 생성 시 history 내역 저장 추가

* feat(#4): 결제 승인 요청 로직 생성

* feat(#4): 결제 취소 로직 생성

* feat(#4): 결제 승인 추가

* feat(#4): order Id로 결제 조회

* refactor(#4): dto 구조 변경

* feat(#4): payment 조회 생성

* feat(#4): message feign client 연결

* feat(#69): payment dto 모듈 생성

* feat(#69): payment internal dto 생성

* 장바구니 API 리팩토링 (#79)

- 장바구니에 필요한 상품 서비스 FeignClient 설정 추가
- 상품 조회 내부 API 로직 변경
* 장바구니 API 리팩토링
- Redis 장바구니 데이터 구조를 상품 ID와 수량만 저장하도록 수정
- 장바구니 상품 추가 시 상품 서비스 API 를 호출하여 상품 존재 여부를 검증하도록 수정
- 장바구니 조회 시 상품 서비스 API 를 호출하여 상품 정보를 가져오는 로직 구현

* 상품 카테고리 CRUD 기능 구현 (#58)

* feat(#50): 카테고리 엔티티 정의
- 셀프참조 형식으로 정의하여 계층형 구조로 관리

* feat(#50): 카테고리 등록 API 구현
- request에서 parentId가 없다면 루트카테고리고 있으면 서브로 들어가게끔 request에 validation 처리를 하지않음
- spring data jpa도 audit 활성화

* feat(#50): 카테고리 수정 API 구현
- 카테고리의 이름, 부모카테고리 아이디를 수정할 수 있음
- 반환시 해당 카테고리에 있는 subCategory들도 한번에 볼수있게 함

* feat(#50): 카테고리 삭제 API 구현
- soft delete처리, 해당 카테고리를 parent로 가지고 있는 카테고리들도 삭제

* feat(#50): 전체 카테고리 조회 API 구현
- 패치조인으로 조회하여 서브카테고리들까지 한번에 조회
- 배치사이즈를 10으로 조정하여 10개가 넘는 카테고리 목록이면 나눠서 조회되도록 성능 개선
- 이전 API들의 requestbody 객체들의 validation 기능이 활성화되도록 수정

* feat(#50): 예외 핸들러 추가 등록
- MethodArgumentNotValidException

* feat(#50): 카테고리 캐시 적용
- response에 필요없던 is_deleted 값 삭제

* fix(#50): 카테고리 업데이트 시 서브카테고리 목록의 정보도 업데이트
- 이전 부모 카테고리의 서브카테고리 목록에서 제거해주고, 새로운 카테고리가 있으면 서브카테고리 목록에 넣어주는 작업 진행

* 등급 CRUD 기능 구현 (#73)

* feat(#41): 등급 생성, 조회, 수정, 삭제
- 단위, API 테스트 작성

* Payment internal controller 분리 (#71)

* feat(#4): 결제 모듈 생성

* rename(#4): 폴더 구조 수정

com.sparta.payment.server -> com.sparta.payment

* feat(#4): 결제, 결제내역 Entity 생성

* rename(#4): entity 위치 변경

* feat(#4): 결제 생성 API

- toss payments 연결

* feat(#4): 결제 DB 저장

- user Id String -> Long 변경
- base entity 상속 x -> created_At 추가

* feat(#4): 예외처리 추가

* feat(#4): 결제 생성 시 history 내역 저장 추가

* feat(#4): 결제 승인 요청 로직 생성

* feat(#4): 결제 취소 로직 생성

* feat(#4): 결제 승인 추가

- 결제 완료시 주문 feign api 호출해서  주문 완료 시킬 수 있도록 구현해야 함

* feat(#4): order Id로 결제 조회

* refactor(#4): dto 구조 변경

* feat(#4): payment 조회 생성

payment 단건 조회
payment history 조회
payment 전체 조회
order Id로 payment 조회

* feat(#4): message feign client 연결

- 결제 생성시 유저에게 해당 결제 url 전송

* rename(#4): payment internal controller 분리

* rename(#4): dto 위치 수정

* 포인트내역 추가 기능 구현 (#80)

* feat(#72): 포인트 내역 엔티티 추가
- User와 ManyToOne 관계 연결
- PointHistory 관련 Enum 추가

* fix(#72): UserDto 에 point 추가
- getUserByUsername 사용 시 point 반환

* feat(#72): 포인트 내역 추가 API 생성
- 포인트 내역 추가 시 유저 포인트 변동

* fix(#72): 포인트 Integer > BigDecimal 로 수정
- 주문에서 포인트 계산 시 통일성을 위해
- 이후 포인트에 소수점이 들어갈 확정성 고려

* 배송지 생성, 배송지 단일 조회 (#83)

* feat(#75): 배송지 엔티티 생성
- User와 ManyToOne 관계 연결

* feat(#75): 배송지 생성

* feat(#75): 배송지 단일 조회

* 포인트 적립 및 사용 시 사용되는 Dto 수정 (#84)

* fix(#72): point request > user_dto에 pointHistoryDto로 수정
- 내부 메서드인데 외부 메서드처럼 만들어버림

* �상품목록 검색 API 구현 (#82)

* chore(#59): elastic search, kibana에 인증 기능 활성화
- ssl 접속을 위해 security를 enable
- es 노드를 es01, es02, es03으로 구성
- 사전에 .env 세팅 필요

* chore(#59): es ssl 연결을 위한 계정정보 설정

* fix(#59): 할인정책이 없으면 discountedPrice에 originalPrice를 세팅하도록 변경

* feat(#59): 상품 목록조회 API 구현
- 카테고리 별/필터링 조건 별/정렬 별 조회를 수행하는 API
- elastic search에 java api로 직접 search 쿼리를 보내는 것으로 수행
- 현재 일시적으로 s JsonIgnoreProperties를 허용했으나 추후 수정예정

* docs(#59): update docker-compose.yml
- 덮어쓰기 되면서 누락된 product-cache 서비스를 원복

* 상품에 인증필터 적용 (#90)

* feat(#89): product server에 인증필터 추가
- security 의존성 추가

* chore(#89): product server 모듈 이름 변경

* 이벤트 쿠폰 생성 및 발급 기능 구현 (#87)

* feat(#81): promotion 모듈 추가
- 쿠폰 생성 및 이벤트 쿠폰 발급 기능 구현 예정

* feat(#81): 쿠폰 Entity 생성
- 쿠폰, 할인 enum 추가
- Promotion 에러 처리를 위한 코드 추가

* feat(#81): 이벤트 쿠폰 생성 API 구현
- 이벤트 테이블 추가 시 수정 필요

* feat(#81): 유저 쿠폰 Entity 생성

* feat(#81): 이벤트 쿠폰 발급 기능 구현

* feat(#81): 프로모션에 인증 객체 기능 import
- 이벤트 쿠폰 발급 시 인증 객체에서 유저 ID 가져오도록 수정

* fix(#81): 동시성 이슈 해결을 위한 비관적 락 사용

* CI 파이브라인 수정 (#78)

* fix(#77): CI 파이브라인 수정
- 여러 개의 서비스 빌드 과정 수정

* 결제 API 부분 수정, es 저장  (#86)

* rename(#85): mapping 경로 수정

* feat(#85): 결제 내역 es 저장 로직 추가

* feat(#85): security 필터 추가

* feat(#85): 결제 조회 queryDsl 추가

* 배송지 관련 기능 구현 (#92)

* fix(#75): 유저 권한 수정
- ROLE_CUSTOMER > ROLE_USER

* feat(#75): 내 배송지 조회 기능 구현

* feat(#75): 배송지 전제 조회

* feat(#75): 배송지 수정

* feat(#75): 배송지 삭제

* 상품 등록시 카테고리 검증 및 재고감소 내부 API 구현 (#93)

* rename(#88): 서비스를 product, category 패키지로 구분

* feat(#88): 상품등록, 수정시 카테고리 검증 로직 추가

* feat(#88): 주문시 재고감소 내부 API 구성
- 추후 동시성처리, 감소못할시 예외처리 구현이 필요 (주문개발에서 진행)

* feat(#88): 성능 비교를 위한 카산드라db에서 조회해오는 상품목록 조회 API 구현

* 결제 수정사항 반영 (#94)

* rename(#85): mapping 경로 수정

* feat(#85): 결제 내역 es 저장 로직 추가

* feat(#85): security 필터 추가

* feat(#85): 결제 조회 queryDsl 추가

* refactor(#85): 결제 완료 url 환경변수로 변경

* fix(#85): elastic search throw 제거

* feat(#85): 결제 성공시 화면 생성

* feat(#85): 결제 성공시 kafka 이벤트 발행

* 사전예약 등록, 수정, 삭제, 조회 API 구현  (#98)

* fix(#96): product 서버 라우팅 정보 변경
- 사전예약주문의 엔드포인트는 /preorders

* feat(#96): 사전예약주문 등록, 수정, 삭제, 읽기, 오픈, 취소 API 구현
- 등록, 수정시 현재 product 수량보다 적은 수량만 예약가능수량으로 등록할 수 있음
- 조회시 isPublic true인것들만 조회되도록 함
- 삭제시 soft delete처리
- 취소상태로 변경시 isPublic을 false로 처리함 추후 해당 사전예약상품을 주문, 결제한 상태도 cancelled상태로 전파시켜야함

* elastic search 검색엔진 (#105)

* feat(#76): search 모듈 생성

* feat(#76): keyword search 기능 생성

* feat(#76): 검색 필터링 추가

* feat(#76): exception 처리 로직 추가

* fix(#76): keyword 조회시 전체 검색되는 에러 수정

* feat(#76): keyword field 추가, size filter 추가

* feat(#76): sortOption 추가

* feat(#76): 정렬 조건에 리뷰순 추가

* 자동 배포 진행 (#97)

* feat(#95): docker file 및 compose 작성

* feat(#95): gitAction CI/CD flow에 배포 flow 추가

* feat(#95): git action에 artifact 업로드 및 다운로드 추가
- gitaction 환경 내에서 build 시 jar 파일을 찾지못함. artifact를 이용하여 업로드하고 Docker 작업 시 download

* refactor(#95): eureka 서비스에 server 폴더 추가
- gitaction에서 빌드 시 경로 통일을 위해

* fix(#95): Dockerfile을 변수로 설정
- local과 prod에서 복사할 파일이 다름
- local에서 실행할 때는 사용할 서비스가 빌드되어 *.jar 파일이 만들어진 상태여야 함

* fix(#95): gitAction에서 Docker, Deploy는 dev에 push 할 때만 진행

* feat(#95): 배포에 order 모듈 추가
- DB_PASSWORD 값 추가
- RDS 비밀번호 바꿔야 함

* feat(#95): 배포 시 ec2에서 기존에 저장된 모든 이미지 제거 옵션 추가

* feat(#95): 사용 중인 포트 종료 스크립트 추가

* fix(#95): build는 pr, push에서 둘 다 진행. 배포만 push에서 진행하도록 수정 (#110)

* 주문 생성 API (#111)

- 주문 엔티티 생성
- 주문 생성 로직 작성
- 포인트 사용 금액을 BigDecimal 로 변경
- 주문하는 상품의 쿠폰 사용 가능 여부 검사 추가
- 주문할 상품의 정보 조회 및 재고 확인 로직 구현
- 고유한 주문 생성 및 주문 상품 엔티티 생성 로직 구현
- 장바구니에서 주문한 상품 삭제 기능 추가
-  User 서비스에 사용자 ID로 조회하는 API 구현
- Order 서비스 사용자 인증 객체 연결
- 주문 생성 API 배송지 조회, 포인트 사용 연결
- 주문 생성 실패 시 사용자 포인트 롤백 로직 구현
- 주문 생성 실패 시 재고 감소 롤백 로직 구현
- 주문 생성 실패 시 롤백 로직 구현

* 결제 배포용 yml 생성 (#101)

* delete(#99): elastic 관련 설정 제거

* delete(#99): 기본 yml, prod yml 파일 생성

* 기본 yml, prod yml 생성 (#103)

* 검색 엔진 기본 yml, prod yml 생성 (#107)

* dev에 동시에 여러개가 merge 될 경우, 이전에 실행 중이던 dev 브랜치의 워크플로우가 취소 (#113)

* feat(#95): dev에 동시에 여러개가 merge 될 경우, 이전에 실행 중이던 dev 브랜치의 워크플로우가 취소
- 동시에 여러개가 merge 될 경우, 깃 액션은 이걸 병렬로 처리한다. 병렬로 처리할 경우, 리소스 낭비며 배포 시 충동을 발생시킬 수 있다.

* 이벤트 CRUD (#114)

* feat(#109): 이벤트 CRUD

* feat(#109): event 예외처리

* feat(#109): payment, search route 추가

* 결제 모듈 배포 진행 (#116)

* fix: docker compose에 결제 모듈 포트 변경

* 슬랙 모듈 배포 (#117)

- github secrets에 SLACK_TOKEN 값 추가
- docker-compose에 슬랙 컨테이너 추가
- slack prod 값 수정
- ecr 생성
- payment 스키마에 슬랙 테이블 추가

* 상품 모듈 배포 (#118)

- github secrets에 상품 컨테이너에 필요한 값 추가
- docker-compose에 상품 컨테이너 추가
- product application-prod.yml 생성
- product ecr 생성
- cassandra, kibana, elasticsearch 추가

* feat: 상품 배포 시 필요한 환경 변수 추가

* chore: 깃 액션에서 상품 배포 시 필요한 환경 변수 추가

* chore: 불필요한 컨테이너 정리 옵션 추가

* 결제 완료 이벤트 구독 (#119)

* feat(#115): kafka listener를 통한 결제 완료 이벤트 구독

* feat(#115): prod yml kafka 추가

* chore: 불필요한 이미지 정리 옵션 및 19061 포트 확인 코드 추가

* 주문 취소 API 구현 (#120)

* fix: elasticsearch fingerprint ec2에서 설정한 값으로 수정

* 프로모션 모듈 배포 (#121)

- promotion application.yml 분리 (local , prod)
- promotion ecr 생성
- promotion 스키마 생성

* 주문 API와 결제 API 연결 (#122)

- 주문 취소 API 구현
- 주문 생성 - 결제 연결
- order 모듈 payment_dto로 실행되는 오류 해결

* search 모듈 배포 (#125)

- search ecr 추가

* ec2 환경에서 서비스 실행 시 DB 비밀번호 문제(#124)

* chore(#95): 런타임 시 환경 변수 사용하도록 수정

* chore: search 모듈에 환경 변수 추가

* 주문 상세조회 API (#126)

* feat(#112): 주문 취소 API 구현

* feat(#112): 주문 취소 API 구현

* feat(#112): 충돌 해결

* feat(#112): 주문 생성 - 결제 연결

* feat(#112): 주문 생성 - 결제 연결 완료

* fix(#112): order 모듈 payment_dto로 실행되는 오류 해결

* feat(#112): 주문 상세조회 API 구현

* chore: 배포환경에서 카산드라 contact-points 설정

* chore: 배포환경에서 elasticsearch host 설정

* chore: 배포환경에서 search 모듈 elasticsearch host 설정

* 사전예약주문 API 구현  (#127)

* feat(#100): 카프카에서 사용하는 토픽들을 관리하는 문자열 상수 클래스를 commons에 정의

* feat(#22): Dto 모듈에 OrderDto 생성

* chore(#100): 카프카 설정 및 PreOrderProducer 등록
- 카프카 의존성 및 설정
- 오더서버로 사전예약상품 정보를 전송하는 카프카 빈 추가

* rename(#100): ProductSearchDto를 utils 패키지로 이동

* feat(#100): 사전예약주문 API 구현
- Redission 으로 분산락 구현
- validate로 사전예약주문기간, 중복여부, 사전예약수량 여부 확인

---------

Co-authored-by: linavell <linavell@naver.com>

* docs: update application-prod.yml

* fix: 시나리오 1 에러 수정

- 상품 검색/조회할때 로그인 해야 조회되는 에러
- 결제 완료 후에 나오는 페이지 권한 없음(403) 에러

* chore: 카프카 설정 수정

* chore: 카프카 설정 수정 > 0.0.0.0으로 변경

* chore: 카프카 설정 수정 > 내부 아이피로 변경
- OUTSIDE는 필요없는 거 같음

* search query 수정, 상품 검색/조회 403 에러 수정 (#130)

* fix: 시나리오 1 에러 수정

- 상품 검색/조회할때 로그인 해야 조회되는 에러
- 결제 완료 후에 나오는 페이지 권한 없음(403) 에러

* fix(#129): search 쿼리 수정

* fix: paymentService userId 누락된 값 추가

* fix: filter chain에 product/search 경로 추가

* fix: user Id 누락된 값 추가

* fix: gateway 라우팅 수정

* chore: kafka 환경 변수 수정

* chore: swap 메모리 초기화 설정

* �주문서버에 사전예약 리스너 빈 등록  (#131)

* feat(#128): elastic search dto들에서 stock값 제외

* feat(#128): order 서버에 사전주문예약을 받는 리스너 빈 등록
- OrderCreateService의 createOrder에서 dto import 필요

* 유저 엔티티에 이메일 컬럼 추가 (#134)

- 이메일 추가에 따른 dto, test 수정

* 사전예약 로직 수정 (#135)

* fix(#128): 불필요한 조회 제거, 사전예약 캐시 데이터에 Product 아이디 추가

* feat(#128): 사전예약정보 변경시 캐싱 되어있는 정보 삭제, 오픈되어있는 사전예약정보만 저장할 수 있도록 진행

* 상품서버 API 인가처리 및 AuditorAware 기능 추가 (#137)

* feat(#104): AuditorAware 기능 활성화
- createdBy, updatedBy에 username 자동으로 넣어주기

* chore(#104): 전채 공개인 조회쿼리들 permitAll처리
- 전체조회 구분을 위한 엔드포인트 search 추가
- 필터체인에서도 permit all
- 게이트웨이에도 패스하는 로직 추가

* feat(#104): securityConfig에 커스텀 핸들러 등록

* feat(#104): product 서버 API들에 인가처리
- ControllerAdvice에 핸들러 추가
- 403 퍼미션 예외 등록
- 내부 로직 확인용으로 썼던 API들 제거

* 주문 생성 오류 해결 및 주문 관련 API 구현 (#136)

- 카프카 객체 통일을 위한 OrderCreateRequest 경로 수정
- 장바구니 재고 수량 이상으로 담아지는 오류 수정
- 장바구니에 없는 상품 주문 시 결제 url 전송되는 오류 수정
- 주문 취소 / 결제 실패 시 주문 취소 로직 분리하여 구현
- 주문 상태 변경 API 구현
- 내 주문 조회 API 구현
- 사용자 internal dto email 적용 및 결제 이벤트 발행 오류 해결

* 쿠폰 관련 기능 구현 (#138)

- 쿠폰 전체 조회 API
- 쿠폰 단일 조회 API
- 특정 사용자 쿠폰 전체 조회 API
- 내 쿠폰 전체 조회 API
- 내 쿠폰 수정 API
- 내 쿠폰 삭제 API
- 내 쿠폰 사용 및 환불 API

* 사용자 관련 기능 추가 (#139)

* feat(#13): @EnableJpaAuditing 추가

* feat(#13): 마이페이지 조회 API 구현

* feat(#13): 사용자 단일 조회 API 구현

* feat(#13): 사용자 전체 조회 API 구현
- 인증/인가 테스트 API 삭제

* feat(#13): 사용자 비밀번호 재설정 API

* feat(#13): UserControllerAdvice 추가

* feat(#13): 유저 삭제 API
- soft delete 처리

* 사용자 등급 관련 기능 (#141)

* feat(#74): 사용자 등급 Entity 추가
- 유저와 OneToOne 관계
- 등급과 ManyToOne 관계

* feat(#74): 회원가입 시 사용자 등급 추가
- 회원가입 로직 수정
- 회원가입 단위 테스트 수정

* feat(#74): 현재 사용자 등급 조회 API

* feat(#74): 특정 사용자 등급 조회 API

* feat(#74): 전체 사용자 등급 조회 API

* feat(#74): 사용자 등급 수정 API

* 주문 관련 API 마무리 (#142)

* feat(#140): 주문 주소지 변경 API 구현

* feat(#140): 주문 송장번호 등록 API 구현

* feat(#140): 주문 내역 삭제 API 구현

* feat(#140): 주문 전체 조회 API 구현

* 포인트 내역 기능 구현 (#143)

* feat(#72): 특정 사용자 포인트 조회 API
- pageable 추가. 그에 따른 로직 수정

* feat(#72): 전체 사용자 포인트 조회 API

* feat(#72): 단일 포인트 내역 삭제 API

* fix: merge 시 , 빼먹음

* 주문 시 재고 감소, 재고 롤백 동시성 처리 (#147)

* feat(#145): 재고 감소, 롤백 동시성 처리
* feat(#145): 재고 감소, 롤백 동시성 처리

* 배포 리펙토링 및 카프카 UI 추가 (#149)

* chore(#148): docker compose 파일 분리
- 우리가 만든 서비시의 이미지와 외부 서비스 이미지를 분리
- 최초로 EC2 서버 실행 시 외부 서비스 이미지를 먼저 실행하고 배포를 진행해야 함 -> EC2에 접속하여 직접 진행
- docker 이미지 빌드 시 용량을 줄이기위해 slim 버전 사용 > 내부에서 build를 안하는데 build 버전을 쓰고 있었음

* chore(#148): CI, CD 분리
- dev에 PR시에는 CI만 실행
- dev에 Push시에는 CD만 실행

* chore(#148): 카프카 UI 추가

* chore(#148): 배포 환경에서 jwt secert key 환경변수로 사용

* chore(#148): 데이터소스 설정 간소화: datasource의 URL 및 username을 치환

* 외부 저장소에 상품이미지 업로드 기능 구현  (#150)

* feat(#91): AWS s3Client 설정
- 의존성 추가
- AWS Credentials 값들 추가
- product origin 버킷에 상품 원본 이미지 저장

* feat(#91): 상품 추가, 변경, 삭제 로직에 이미지 로직 추가
- 컨트롤러 request를 form-data형식으로 변경
- 생성, 수정 request에서 url제거, response에 추가
- originImgUrl, detailImgUrl, thumbnailImgUrl로 저장
- 수정시 업데이트된 이미지 저장하면서 이전 이미지는 삭제

* fix: product 환경변수명 변경 및 profile local로 변경

* chore: 도커 파일 내에 profile을 정하는 환경 변수 추가
- CI.yml, CD.yml에서 -D spring.profiles.active=prod 옵션 제거 > JVM에서 사용하는 옵션임

* 쿠폰 발행 기능 고도화 (#153)

* feat(#81): 쿠폰 발급 시 동시성 문제 해결을 비관적 락에서 분산 락으로 변경

* feat(#81): 쿠폰 발행 시 kafka 적용

* feat(#81): 쿠폰 생성 시 이벤트 유무 검사

* feat(#81): 쿠폰 발급과 사용자 쿠폰 조회 시 User 모듈을 통해 해당 유저가 존재하는지 확인

* fix: 쿠폰 발행 리스너 쪽에 로그 작성 및 주문 모듈 쪽 KafkaListener topics 이름 치환

* ELK 모니터링 시스템 (#155)

* chore(#146): 모니터링을 위한 서비스 추가
- logstash, filebeat, metricbeat 설정 관련 yml파일들

* chore(#146): product 서버 Logstash 설정

* chore(#146): application log 수집을 위한 Logstash 설정

---------

Co-authored-by: harper <35358294+yooyouny@users.noreply.github.com>

* fix(#91): 썸네일 이미지 경로도 함께 만들어서 저장 (#152)

* chore(#146): logstash conf 추가 (#156)

* 사전 예약 주문 생성 오류 해결 (#157)

fix(#154): 사전 예약 주문 생성 오류 해결 (null 체크 추가)

* chore: logstash 전송 IP 변경

* chore: logstash 전송 IP 변경

* delete: search log 제거

* chore: logstash 경로 이름 변경

* Gateway 대기열 도입 (#158)

* feat(#114): QueueFilter 추가

* feat(#114): QueueFilter 추가

* feat(#114): 사용자 활동 추적

proceed queue 내에 있는 사용자 활동 추적, 5분 이상 활동이 없으면 proceed queue에서 제거

* feat(#114): gateway Exception

* feat(#114): docker compose 수정

gateway-cache 추가

* feat(#114): MAX_ACTIVE_USERS 환경변수로 변경

* feat(#114): prod-yml gateway cache 추가

* feat(#114) : 429 error에서 현재 대기 순위 반환해주도록 리턴 변경

wait queue에서 대기시
기존 : 대기열 진입 후 429 에러 반환
변경 : 대기열 진입 후 대기 순위(rank) 반환

* refactor(#114) : active queue 제거 및 코드 간소화

* feat(#114): thread pool, redisson 설정

* feat(#114): redisson 분산락 적용

* Create README.md

* fix: 에러 로직 수정

isAllowed 누락

* fix: 에러 로직 수정

* fix: gateway 에러 로직 수정

- isAllowed 함수 누락 수정
- payment 인가 수정

* Update README.md

* fix: payments 경로 수정

---------

Co-authored-by: kyeonkim <108860425+kyeonkim@users.noreply.github.com>
Co-authored-by: Kim Jin Sun <122031650+kimzinsun@users.noreply.github.com>
Co-authored-by: eggnee <79629309+eggnee@users.noreply.github.com>
Co-authored-by: kyeonkim <kyeonkim5021@gmail.com>
Co-authored-by: linavell <linavell@naver.com>
Co-authored-by: Kim JinSeon <kwlstjs00@gmail.com>
  • Loading branch information
7 people authored Nov 1, 2024
1 parent e2bd731 commit f9b40f5
Show file tree
Hide file tree
Showing 406 changed files with 17,753 additions and 83 deletions.
107 changes: 107 additions & 0 deletions .github/workflows/CD.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,107 @@
name: CD

on:
push:
branches: [ dev ]

concurrency:
group: ${{ github.ref }}
cancel-in-progress: true

jobs:
Build:
runs-on: ubuntu-latest
permissions:
contents: read
packages: write
actions: write

steps:
- name: Checkout repository
uses: actions/checkout@v4

- name: Set up JDK 17
uses: actions/setup-java@v4
with:
java-version: '17'
distribution: 'temurin'

- name: Grant execute permission for gradlew
run: chmod +x gradlew

- name: Setup Gradle
uses: gradle/actions/setup-gradle@v4

- name: Build with Gradle
run: ./gradlew clean build -x test

# AWS ECR 에 이미지 업로드 권한을 얻기 위해 인증
- name: Configure AWS credentials
uses: aws-actions/configure-aws-credentials@v4
with:
aws-access-key-id: ${{ secrets.AWS_ACCESS_KEY_ID }}
aws-secret-access-key: ${{ secrets.AWS_SECRET_ACCESS_KEY }}
aws-region: ${{ secrets.AWS_REGION }}

- name: Login to Amazon ECR
id: login-ecr
uses: aws-actions/amazon-ecr-login@v1

- name: Build, Tag and Push docker image to AWS ECR
run: |
docker compose build
chmod +x ./dockerTagAndPush.sh
./dockerTagAndPush.sh
env:
ECR_NAMESPACE: ${{ vars.ECR_NAMESPACE }}
ECR_REGISTRY: ${{ secrets.ECR_REGISTRY }}

Deploy:
name: Deploy
needs: Build
runs-on: ubuntu-latest

steps:
- uses: actions/checkout@v4

# docker compose로 container를 실행하기 위해 docker-compose.yml 을 EC2로 복사
- name: Copy Docker compose file to EC2
uses: appleboy/scp-action@v0.1.7
with:
host: ${{ secrets.EC2_HOST }}
username: ubuntu
key: ${{ secrets.EC2_KEY }}
source: "docker-compose.yml"
target: "/home/ubuntu"

# 사용 중인 포트를 점검하고 종료하는 script를 EC2로 복사
- name: Upload stop-used-port script to EC2
uses: appleboy/scp-action@master
with:
host: ${{ secrets.EC2_HOST }}
username: ubuntu
key: ${{ secrets.EC2_KEY }}
source: "stop-used-port.sh"
target: "/home/ubuntu"

# ssh를 통해 EC2에 접속하고 docker container를 재시작
- name: Deploy to EC2
uses: appleboy/ssh-action@v1.0.3
env:
AWS_ACCESS_KEY_ID: ${{ secrets.AWS_ACCESS_KEY_ID }}
AWS_SECRET_ACCESS_KEY: ${{ secrets.AWS_SECRET_ACCESS_KEY }}
AWS_REGION: ${{ secrets.AWS_REGION }}
ECR_NAMESPACE: ${{ vars.ECR_NAMESPACE }}
ECR_REGISTRY: ${{ secrets.ECR_REGISTRY }}
with:
host: ${{ secrets.EC2_HOST }}
username: ubuntu
key: ${{ secrets.EC2_KEY }}
script: |
aws ecr get-login-password --region ${{ secrets.AWS_REGION }} | docker login --username AWS --password-stdin ${{ secrets.ECR_REGISTRY }}
docker compose down
docker container prune -f
docker rmi $(docker images "${{ secrets.ECR_REGISTRY }}/${{ vars.ECR_NAMESPACE }}/*" -q)
sudo chmod +x /home/ubuntu/stop-used-port.sh && /home/ubuntu/stop-used-port.sh
docker compose pull --quiet
docker compose up -d --no-build
31 changes: 31 additions & 0 deletions .github/workflows/CI.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,31 @@
name: CI

on:
pull_request:
branches: [ dev ]

jobs:
build:
name: Build
runs-on: ubuntu-latest
permissions:
contents: read

steps:
- name: Checkout repository
uses: actions/checkout@v4

- name: Set up JDK 17
uses: actions/setup-java@v4
with:
java-version: '17'
distribution: 'temurin'

- name: Grant execute permission for gradlew
run: chmod +x gradlew

- name: Setup Gradle
uses: gradle/actions/setup-gradle@v4

- name: Build with Gradle
run: ./gradlew clean build -x test
16 changes: 16 additions & 0 deletions Dockerfile
Original file line number Diff line number Diff line change
@@ -0,0 +1,16 @@
# Dockerfile
FROM openjdk:17-jdk-slim

# 시간대 설정
ENV TZ=Asia/Seoul
RUN ln -snf /usr/share/zoneinfo/$TZ /etc/localtime && echo $TZ > /etc/timezone

WORKDIR /app

ENV SPRING_PROFILES_ACTIVE=prod

ARG FILE_DIRECTORY

COPY $FILE_DIRECTORY/build/libs/*.jar /app/app.jar

ENTRYPOINT ["java", "-jar", "/app/app.jar"]
151 changes: 151 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,151 @@
# SASAP!CK : 대규모 트래픽 처리 기반 온라인 쇼핑몰

![타이틀 이미지](https://github.com/user-attachments/assets/1096861f-ab73-42cb-abc2-0b950610cdee)

## 프로젝트 소개

> **SASAP!CK** 프로젝트는 **대규모 트래픽 상황**에서도 안정적인 서비스를 제공하기 위해 **마이크로서비스 아키텍처 (MSA)** 를 기반으로 설계된 쇼핑몰 시스템입니다.
- 블랙프라이데이와 같은 쇼핑 이벤트나 시즌 동안 급증하는 사용자 요청을 원활하게 처리하며 주문, 결제, 사전 예약, 검색, 재고 관리, 쿠폰 등의 핵심 쇼핑 기능을 제공하는 통합 플랫폼 서비스입니다.

- 각 서비스는 독립적으로 확장 가능하도록 설계되어, 높은 유연성을 갖추고 있습니다. 이를 통해 갑작스러운 트래픽 급증 상황에서도 신속한 응답 속도와 서비스의 안정성을 보장하여 UX를 긍정적으로 유지할 수 있습니다.

## 프로젝트 목표

- **대규모 트래픽 대응**
- 스케일아웃을 통해 서버를 분산하여 대규모 트래픽 상황에서도 유저 요청을 안정적으로 처리
- **부하 테스트 및 성능 최적화**
- 주요 비즈니스 API의 처리량을 200.0/sec 이상으로 달성
- 성능 병목 구간을 분석하여 요청 처리 속도를 최적화
- **기술 선택 및 전략 고민**
- 각 기술의 trade-off를 분석하여 서비스 요구 사항에 맞는 최적의 기술과 아키텍처 선택
- 성능, 유지보수성, 확장성을 고려한 전략 수립
- **모니터링 및 CPU 최적화**
- ELK 기반 모니터링 시스템으로 서버 상태와 자원 사용량을 추적
- CPU 성능 최적화를 통해 서버 부하를 줄이고 효율성 향상
- **배포 및 운영**
- 효율성과 일관성을 위해 Docker 및 Docker Compose 사용
- CI/CD 파이프라인을 자동화하기 위해 GitHub Actions와 ECR 사용

## 프로젝트 멤버

| <img src="https://avatars.githubusercontent.com/u/35358294?v=4" width="135" height="135"> | <img src="https://avatars.githubusercontent.com/u/79629309?v=4" width="135" height="135"> | <img src="https://avatars.githubusercontent.com/u/108860425?v=4" width="135" height="135"> | <img src="https://avatars.githubusercontent.com/u/122031650?v=4" width="135" height="135"> |
|:------------------:|:------------------:|:------------------:|:------------------:|
| <a href="https://github.com/yooyouny"><img src="https://upload.wikimedia.org/wikipedia/commons/9/91/Octicons-mark-github.svg" alt="GitHub" width="20" height="20"></a> | <a href="https://github.com/eggnee"><img src="https://upload.wikimedia.org/wikipedia/commons/9/91/Octicons-mark-github.svg" alt="GitHub" width="20" height="20"></a> | <a href="https://github.com/kyeonkim"><img src="https://upload.wikimedia.org/wikipedia/commons/9/91/Octicons-mark-github.svg" alt="GitHub" width="20" height="20"></a> | <a href="https://github.com/kimzinsun"><img src="https://upload.wikimedia.org/wikipedia/commons/9/91/Octicons-mark-github.svg" alt="GitHub" width="20" height="20"></a> |
| 상품, 사전예약주문, <br>모니터링 | 장바구니, 주문, <br>CI/CD | 유저, 인증, <br>쿠폰, CI/CD | 결제, 검색엔진, <br>게이트웨이 대기열, <br>모니터링 |

## 기술 스택

| **분류** | **사용 기술** |
|------------------------|--------------------------------------------------------------------------------------------------|
| **Framework / Library** | Spring Boot, Gradle, Spring Cloud Gateway, Spring Security, Spring Data JPA, QueryDSL, Redisson, AWS Lambda |
| **Messaging** | Apache Kafka |
| **DevOps** | AWS EC2, Docker, Docker Compose, Github Actions, Kibana, LogStash, MetricBeat |
| **Data Source** | AWS RDS (MySQL), AWS S3, Redis, Cassandra, ElasticSearch |
| **Test** | Apache JMeter, Postman, IntelliJ Http Client |
| **External Library** | Slack API, Toss Payments API |

## 배포 링크

| 항목 | URL / 정보 |
|-------------------------|---------------------------------------------------------------|
| **API Docs (Postman)** | [API Docs (Postman)](https://documenter.getpostman.com/view/38424997/2sAY4rDjFF) |
| **Gateway Server** | [http://13.209.108.47:19091](http://13.209.108.47:19091) |
| **System Monitoring (Kibana)** | [http://13.209.108.47:5601](http://13.209.108.47:5601/) |

## 실행 방법

- 추가 예정

## 인프라 설계도

![Infra Diagram](https://github.com/user-attachments/assets/d39ac2c2-8407-4536-a5f6-b9e75f9b35a5)

## 주요 기능

- Elastic Search 기반의 상품 목록 조회 및 검색 서비스 구현
- Toss Payments 테스트 결제 모듈을 이용한 결제 서비스 구현
- Redis Sorted Set을 이용한 게이트웨이 대기열 도입
- Redis 캐싱을 활용한 장바구니/상품 카테고리 기능 구현
- Feign Client 다중 호출 기반 주문 서비스 구현
- Redis Redisson 분산 락과 Apache Kafka를 이용한 서비스 구현
- 쿠폰 발급
- 상품 재고 감소
- 사전 예약 주문
- AWS S3+Lambda를 활용한 외부이미지 저장소 구축
- ELK 스택 기반의 시스템 모니터링 시스템 구축
- CI/CD Pipeline 구축에 GitHub Actions와 AWS ECR 사용

## 시스템 구조도

- **사전 예약 상품 구매 로직**
![사전예약주문](https://github.com/user-attachments/assets/8eda47aa-dfc8-45ba-bbf3-84e494d9dbf6)

- **주문-결제 로직**
![스크린샷 2024-10-23 14 12 19](https://github.com/user-attachments/assets/cca299b6-f7aa-493c-b01b-4d170f3ad21b)

- **게이트웨이 대기열**
![게이트웨이 대기열](https://github.com/user-attachments/assets/60128818-fcc0-471c-bc1b-ba7472f64a32)

- **쿠폰 발급 로직**
![쿠폰 발급 로직](https://github.com/user-attachments/assets/5603b0d5-0e48-412c-8e7c-6ca671bf47b4)

## 기술적 의사결정

1️⃣ **Elastic Search 도입으로 검색 성능 최적화**

- 기존 DB 조회 방식은 전체 테이블을 스캔하는 방식으로 속도가 느리고 대용량 데이터 처리 불가
- 대용량 데이터 처리, 실시간 색인 및 검색이 가능한 Elastic Search 도입
- [상세내용](https://github.com/sasaping/sasaping-system/wiki/Technical-Decision#elastic-search-도입으로-검색-성능-최적화)

2️⃣ **Redis sorted set을 이용한 게이트웨이 대기열**

- 서비스의 전체적인 트래픽을 조절하기 위해 게이트웨이 대기열 도입
- proceed queue, wait queue, active queue를 만들어 사용자 활동 추적
- [상세내용](https://github.com/sasaping/sasaping-system/wiki/Technical-Decision#redis-sorted-set%EC%9D%84-%EC%9D%B4%EC%9A%A9%ED%95%9C-%EA%B2%8C%EC%9D%B4%ED%8A%B8%EC%9B%A8%EC%9D%B4-%EB%8C%80%EA%B8%B0%EC%97%B4)

3️⃣ **상품 저장소를 Cassandra로 선택하여 스케일아웃 상황에 유리하도록 구축**

- 조회성능에 유리한 NoSQL 중 확장성 및 가용성이 더 좋은 카산드라를 메인 저장소로 선택
- 상품 상세조회 외 모든 조회는 ElasticSearch 기반으로 구현함으로써 카산드라의 단점을 보완
- [상세내용](https://github.com/sasaping/sasaping-system/wiki/Technical-Decision#%EC%83%81%ED%92%88-%EC%A0%80%EC%9E%A5%EC%86%8C%EB%A5%BC-cassandra%EB%A1%9C-%EC%84%A0%ED%83%9D%ED%95%98%EC%97%AC-%EC%8A%A4%EC%BC%80%EC%9D%BC%EC%95%84%EC%9B%83-%EC%83%81%ED%99%A9%EC%97%90-%EC%9C%A0%EB%A6%AC%ED%95%98%EB%8F%84%EB%A1%9D-%EA%B5%AC%EC%B6%95)

4️⃣ **Redis 기반 캐싱을 통한 장바구니 및 카테고리 조회 성능 최적화**

- Redis 도입으로 장바구니와 카테고리 데이터 캐싱을 통한 성능 최적화 및 데이터베이스 부하 감소
- 장바구니는 실시간 업데이트 및 30일 TTL 적용, 카테고리 데이터는 빠른 조회를 위한 캐싱 처리
- [상세내용](https://github.com/sasaping/sasaping-system/wiki/Technical-Decision#redis-%EA%B8%B0%EB%B0%98-%EC%BA%90%EC%8B%B1%EC%9D%84-%ED%86%B5%ED%95%9C-%EC%9E%A5%EB%B0%94%EA%B5%AC%EB%8B%88-%EB%B0%8F-%EC%B9%B4%ED%85%8C%EA%B3%A0%EB%A6%AC-%EC%A1%B0%ED%9A%8C-%EC%84%B1%EB%8A%A5-%EC%B5%9C%EC%A0%81%ED%99%94)

5️⃣ **Redisson 분산 락을 활용해 쿠폰발행/재고차감/사전예약수량의 동시성 이슈를 해결**

- Redis의 분산락인 Redisson 도입으로 데이터 무결성을 유지
- 여러 서버에서 동시에 요청이 들어올 경우에도 안전하게 쿠폰발행과 재고차감, 사전예약주문을 진행
- [상세내용](https://github.com/sasaping/sasaping-system/wiki/Technical-Decision#redisson-%EB%B6%84%EC%82%B0-%EB%9D%BD%EC%9D%84-%ED%99%9C%EC%9A%A9%ED%95%B4-%EC%BF%A0%ED%8F%B0%EB%B0%9C%ED%96%89%EC%9E%AC%EA%B3%A0%EC%B0%A8%EA%B0%90%EC%82%AC%EC%A0%84%EC%98%88%EC%95%BD%EC%88%98%EB%9F%89%EC%9D%98-%EB%8F%99%EC%8B%9C%EC%84%B1-%EC%9D%B4%EC%8A%88%EB%A5%BC-%ED%95%B4%EA%B2%B0)

6️⃣ **Kafka를 이용하여 대규모 트래픽 처리 및 모듈 간 비동기 메시지 전송**

- 높은 처리량과 빠른 응답 속도를 제공하기 위해 비동기 처리를 위한 Kafka 도입
- 사전예약주문/쿠폰발행/결제 로직에서 활용
- [상세내용](https://github.com/sasaping/sasaping-system/wiki/Technical-Decision#kafka%EB%A5%BC-%EC%9D%B4%EC%9A%A9%ED%95%98%EC%97%AC-%EB%8C%80%EA%B7%9C%EB%AA%A8-%ED%8A%B8%EB%9E%98%ED%94%BD-%EC%B2%98%EB%A6%AC-%EB%B0%8F-%EB%AA%A8%EB%93%88-%EA%B0%84-%EB%B9%84%EB%8F%99%EA%B8%B0-%EB%A9%94%EC%8B%9C%EC%A7%80-%EC%A0%84%EC%86%A1)

7️⃣ **이미지 저장과 썸네일 생성을 외부에서 처리하여 API 성능 개선**

- 이미지를 DB에 저장하면서 발생하는 오버헤드를 낮추기 위해 외부저장소인 AWS S3에서 처리
- 썸네일 생성도 서버리스인 Lambda에서 처리하여 기존 서버의 책임을 외부로 분할
- [상세내용](https://github.com/sasaping/sasaping-system/wiki/Technical-Decision#%EC%9D%B4%EB%AF%B8%EC%A7%80-%EC%A0%80%EC%9E%A5%EA%B3%BC-%EC%8D%B8%EB%84%A4%EC%9D%BC-%EC%83%9D%EC%84%B1%EC%9D%84-%EC%99%B8%EB%B6%80%EC%97%90%EC%84%9C-%EC%B2%98%EB%A6%AC%ED%95%98%EC%97%AC-api-%EC%84%B1%EB%8A%A5-%EA%B0%9C%EC%84%A0)

## 트러블 슈핑

## 1️⃣ **Elastic Search로 상품목록 조회성능 높이기**

- 상품목록조회는 많은 필터링 조건, 정렬 조건 등으로 많은 컬럼들에 인덱싱 처리가 필요
- 데이터 인덱싱, 빠른 조회를 지원하는 Elastic Search 검색 플랫폼을 도입하여 상세조회만 카산드라에서 조회되고 모든 검색과 목록 조회는 Elastic Search 기반으로 진행되도록 구현
- Elastic Search 도입으로 상품목록 조회 API 처리량이 **약 114.3% 증가한 성과를 얻음**
- [상세내용](https://github.com/sasaping/sasaping-system/wiki/Trouble-Shooting#1%EF%B8%8F%E2%83%A3elastic-search%EB%A1%9C-%EC%83%81%ED%92%88%EB%AA%A9%EB%A1%9D-%EC%A1%B0%ED%9A%8C%EC%84%B1%EB%8A%A5-%EB%86%92%EC%9D%B4%EA%B8%B0)

## **2️⃣ 분산락과 Kafka를 사용하여 쿠폰 발급 시 발생하는 문제점 개선**

- 대규모 트래픽 환경에서 쿠폰 발급 시 쿠폰 수량이 공유자원이므로 동시성 이슈가 발생
- 비관적 락을 통해 동시성 문제를 해결하였으나 분산 서버에 맞지 않는다고 판단. 또한, 낮은 처리량으로 인해 분산락 + Kafka를 통해 문제점 개선
- 분산락과 Kafka 도입 후 쿠폰 발급 API 처리량이 **약 344% 이상 향상**
- [상세내용](https://github.com/sasaping/sasaping-system/wiki/Trouble-Shooting#2%EF%B8%8F%E2%83%A3%EB%B6%84%EC%82%B0%EB%9D%BD%EA%B3%BC-kafka%EB%A5%BC-%EC%82%AC%EC%9A%A9%ED%95%98%EC%97%AC-%EC%BF%A0%ED%8F%B0-%EB%B0%9C%EA%B8%89-%EC%8B%9C-%EB%B0%9C%EC%83%9D%ED%95%98%EB%8A%94-%EB%AC%B8%EC%A0%9C%EC%A0%90-%EA%B0%9C%EC%84%A0)
22 changes: 11 additions & 11 deletions build.gradle
Original file line number Diff line number Diff line change
@@ -1,28 +1,28 @@
plugins {
id 'java'
id 'org.springframework.boot' version '3.3.4'
id 'io.spring.dependency-management' version '1.1.6'
id 'java'
id 'org.springframework.boot' version '3.3.4' apply(false)
id 'io.spring.dependency-management' version '1.1.6' apply(false)
}

group = 'com.sparta'
version = '0.0.1-SNAPSHOT'

java {
toolchain {
languageVersion = JavaLanguageVersion.of(17)
}
toolchain {
languageVersion = JavaLanguageVersion.of(17)
}
}

repositories {
mavenCentral()
mavenCentral()
}

dependencies {
implementation 'org.springframework.boot:spring-boot-starter'
testImplementation 'org.springframework.boot:spring-boot-starter-test'
testRuntimeOnly 'org.junit.platform:junit-platform-launcher'
implementation 'org.springframework.boot:spring-boot-starter'
testImplementation 'org.springframework.boot:spring-boot-starter-test'
testRuntimeOnly 'org.junit.platform:junit-platform-launcher'
}

tasks.named('test') {
useJUnitPlatform()
useJUnitPlatform()
}
16 changes: 16 additions & 0 deletions common/domain/build.gradle
Original file line number Diff line number Diff line change
Expand Up @@ -23,12 +23,28 @@ repositories {
mavenCentral()
}

sourceSets {
main {
java {
srcDirs = ['src/main/java', 'src/main/generated']
}
}
}


dependencies {
implementation 'org.springframework.boot:spring-boot-starter'
implementation 'org.springframework.boot:spring-boot-starter-data-jpa'
compileOnly 'org.projectlombok:lombok'
annotationProcessor 'org.projectlombok:lombok'
testImplementation 'org.springframework.boot:spring-boot-starter-test'
testRuntimeOnly 'org.junit.platform:junit-platform-launcher'

// QueryDSL
implementation 'com.querydsl:querydsl-jpa:5.0.0:jakarta'
annotationProcessor "com.querydsl:querydsl-apt:5.0.0:jakarta"
annotationProcessor "jakarta.persistence:jakarta.persistence-api"
annotationProcessor "jakarta.annotation:jakarta.annotation-api"
}

tasks.named('test') {
Expand Down
Loading

0 comments on commit f9b40f5

Please sign in to comment.