springboot6 상품 목록 조회 기능 개선 — 인덱스 → 캐시 → Redis 적용 과정 조회 기능 개선을 맡았을 때 처음 든 생각은 단순했다.“인덱스 몇 개 추가하면 끝나겠지.”예전에 이런 경험이 있었기 때문이다.[MariaDB] OFFSET 페이징 & JOIN이 느릴 때 MariaDB 인덱스 최적화 경험그때는 인덱스로 대부분 해결됐다.그래서 이번에도 비슷할 거라고 생각했다.하지만 실제로는 조회 API마다 해결 방법이 완전히 달랐다. 성능 개선 대상 API내가 개선해야 하는 조회 API는 총 5개였다. UC설명APIUC-1전체 조회 + 최신순/api/v1/products?page=0&size=20UC-2전체 조회 + 좋아요순/api/v1/products?sort=likes_descUC-3브랜드 필터 + 최신순/api/v1/products?brandId=1UC-4브랜드 필터 + 좋아요순/ap.. 2026. 3. 13. [Java / Spring Boot] 브랜드에서 전화가 왔다, "우리 상품 좋아요가 한번에 수십개씩 빠져요!" - 5편 좋아요 카운트 로직을 짜다가 문제를 발견했다."약간의 오차는 괜찮다"고 판단하고 비동기로 처리했는데, 코드를 들여다보니 수십 개씩 틀어질 수 있는 구조였다.실제로 운영 중에 이런 상황이 생기면 어떻게 될까? 가상의 브랜드 담당자에게 "좋아요 수가 갑자기 수십 개씩 줄었다가 돌아와요"라는 연락을 받는다고 상상해보자. 처음엔 식은땀이 날 것 같다. "약간의 오차는 괜찮다"고 했는데, "약간의 오차"와 "수십 개씩 튀는 것"은 달랐다.원인을 찾아보자.정규화 vs 비정규화좋아요 수를 보여주는 가장 자연스러운 방법은 이거다.SELECT COUNT(*) FROM likes WHERE product_id = 1이게 정규화 방식이다. 데이터를 중복 없이 한 곳에만 저장하고, 필요할 때 계산한다.정규화:장점 → 데이터 .. 2026. 3. 6. [Java / Spring Boot] 쿠폰 사용에 대한 처리는 어떤 락이 적절할까 - 4편 3편 마지막에 이런 질문을 던졌다.(3편: 비관적 락 vs 낙관적 락, 선택 기준은 무엇이었나 - 3편)유니크 키는 어디에 쓰는 걸까?쿠폰 로직을 구현하면서 답을 찾았다.재고 vs 쿠폰: 충돌 패턴이 다르다재고는 여러 사람이 하나를 두고 경쟁하는 문제다. 쿠폰은 다르다.재고 차감: 불특정 다수가 동시에 같은 상품에 달려듦쿠폰 발급: 동일 사용자의 중복 요청이 문제쿠폰 사용: 같은 쿠폰으로 동시에 두 번 주문 시도충돌 주체가 다르니까 전략도 달라야 한다.쿠폰 중복 발급: DB 유니크 키로 막는다애플리케이션 코드에서 이렇게 체크하면 충분할 것 같다.@Transactionalpublic void issue(Long userId, Long couponId) { boolean exists = us.. 2026. 3. 6. [Java / Spring Boot] 비관적 락 vs 낙관적 락, 선택 기준은 무엇이었나 - 3편 2편에서 재고 차감에 비관적 락을 적용했다. 그런데 모든 상황에 비관적 락이 정답은 아니다.(2편: 스투시 반팔티를 10명이 동시에 주문했을 때 발생한 일-2편 )비관적 락은 하나씩 순차 처리라 병목현상이 생기고, 데드락 위험도 있다.충돌이 거의 없는 상황에서도 락을 걸면 비용만 크고 얻는 게 없는 상황이 된다.충돌 빈도가 다르다재고 차감: 불특정 다수가 동시에 같은 상품에 달려듦 → 충돌 빈도 높음게시글 수정: 보통 작성자 혼자 수정 → 충돌 빈도 낮음게시글 수정에 비관적 락을 걸면 어떻게 될까?작성자가 수정 버튼 클릭→ SELECT FOR UPDATE (배타 락 획득)→ 수정 폼에서 내용 입력 중... (30초)→ 저장 클릭 → 커밋 → 락 해제이 30초 동안 배타 락이 걸려있다. 다른 사람들은 .. 2026. 3. 6. 이전 1 2 다음 반응형