전체 글 64

인덱스를 걸었는데 왜 전체 응답은 18%밖에 안 줄었을까?

들어가며프로젝트로 e-커머스 서비스를 만들고 나니, 한 가지가 궁금해졌습니다. "부하가 몰리면 어디서부터 느려질까?"k6로 부하 테스트를 시작했습니다.처음엔 "느린 쿼리에 인덱스를 걸면 되겠지" 정도로 가볍게 생각했지만, 측정을 거듭할수록 숫자를 만들어낸 조건을 의심하지 않으면 엉뚱한 결론에 도달한다는 것을 확인하게 됐습니다.이 글에서 다루는 것:부하 테스트 데이터를 현실적으로 설계하는 법, 그리고 그러지 않았을 때 생기는 함정인덱스 / 격리 실험 / 커넥션 풀 메트릭으로 병목을 단계적으로 증명하는 과정캐시로 병목을 해소하고, 그다음 병목이 드러나기까지1. 시작은 내 실수였다 — "인덱스로 58% 개선"의 함정처음엔 단순했습니다. k6로 부하를 돌려보니 주문목록 조회가 3초 넘게 걸려 유독 느렸고, EX..

Development 2026.06.04

내가 본 사용자가 왜 다음 페이지에 또 나올까? 페이징의 본질적인 결함 해결하기

게시판, 알림 내역, 결제 히스토리 등 리스트가 있는 곳이라면 어디든 페이징 처리가 들어갑니다.보통 최신순(DESC)으로 정렬하고 페이지 번호를 눌러 이동하는 방식을 당연하게 사용하곤 합니다. "방금 1페이지에서 본 주문이 2페이지에 또 나와요." "주문 리스트를 넘기다 보니 중간에 주문 몇 개를 건너뛴 것 같아요." 로직에는 아무런 문제가 없는데 왜 이런 일이 생길까요?이는 Offset과 Limit을 기반으로 하는 전통적인 페이징 방식이 실시간으로 추가되는 데이터를 고려하지 못해 발생하는 '데이터 밀림(Data Shifting) 현상'입니다.새로운 데이터가 리스트 최상단에 추가되는 순간, 우리가 정해놓은 페이지의 경계가 무너지기 때문에 발생합니다.오늘은 이 문제가 발생하는 근본적인 원인을 분석하고, 제..

Development 2025.12.30

10배 빨라진 에러 대응, 우리 팀의 새로운 에러 시스템 구축기

이번 포스트는 사내 에러봇을 만든 경험기를 풀어보려고 합니다. 에러봇 개발기: 에러봇으로 에러 대응 속도 10배 올리기B2C 서비스를 운영하는 개발자라면 누구나 한 번쯤 겪어봤을 겁니다. 밤늦게까지 서비스 상태를 확인하고, 새벽에 울리는 고객 문의에 가슴 졸이던 경험 말이죠. 저희 팀 역시 마찬가지였습니다.에러가 발생해도 파악이 늦고, 어디서 문제가 터졌는지 몰라 고객 경험은 나빠지고, 신속한 개발은 엄두도 못 내는 악순환이 계속됐습니다. 이런 문제를 근본적으로 해결하고자 저는 사내 에러봇 개발을 결심했습니다.이 글은 에러 모니터링 시스템이 전무했던 저희 팀이 어떻게 에러봇을 구축하고, 효율적인 에러 대응 시스템을 갖추게 되었는지에 대한 경험담입니다. 에러, 어디서 터졌니?기존에는 서비스에 장애가 발생해..

Development 2025.09.24

[TEST] TestCoverage 100%에 도달해보자.

문득 진행했던 프로젝트명이 TDD인데 테스트 커버리지 0%인 걸 보고 그래도 이름에 맞게 커버리지 80%까지는 올려보자 라는 생각으로 작성을 시작했다.하지만..테스트 코드를 작성하다 보면 자주 겪는 문제 중 하나는 바로 시간 관련 로직을 처리할 때 발생합니다. 특히, LocalDate.now()와 같은 시간을 직접적으로 로직 내에서 사용하면 테스트 코드가 실행되는 날마다 값이 달라져 테스트가 실패하는 문제가 발생합니다.시간에 의존적인 테스트 예를 들어 다음과 같은 코드가 있습니다:if (LocalDate.now() == todo.deadline) { // 특정 로직 수행}이 코드의 문제점은 테스트가 실행되는 날짜가 매번 바뀌기 때문에, 실행하는 날에 따라 테스트 결과가 달라질 수 있다는 것입니다.처..

TEST 2025.05.20

[TEST] RestDocs와 Kotlin DSL로 직관적인 테스트 코드를 작성해보자.

저는 최근 Spring RestDocs를 활용하여 REST API를 문서화하는 작업을 했습니다. 하지만 RestDocs를 기본적인 형태로 사용하면 다음과 같은 코드가 만들어지곤 합니다.requestFields( fieldWithPath("username") .type(JsonFieldType.STRING) .description("회원 이름"), fieldWithPath("avatarUrl") .type(JsonFieldType.STRING) .description("GitHub 프로필 URL"), fieldWithPath("gitUrl") .type(JsonFieldType.STRING) .description(..

TEST 2025.05.16

[Distance] API 요청 과부하로부터 서비스를 보호하자.

Distance서비스를 운영하면서 사실 마냥 순탄치는 않았습니다.서비스를 운영하면서 겪었던 문제 중 하나인 "Postman을 통한 무한 API요청"을 효과적으로 차단한 경험을 공유하려 합니다. 저희 서비스는 축제 시즌에 배포된 서비스인데 00대학교에 배포 중 갑자기 오후 11시쯤에 Slack으로 알림하나가 날라왔습니다.이 에러는 저희 서비스에 굉장한 크리티컬한 에러였습니다.사용자가 Distance서비스에 신규 가입을 하려면 반드시 SMS인증을 통해 가입을 할 수 있는데 그 인증 API가 일일 사용량 초과가 된 것입니다.분명 일일 한도가 약 390건 정도가 남아있었는데 이게 한 순간에 사라진게 이상하게 생각해 발송내역을 보니 한 번호가 391건의 요청을 했던 것을 확인할 수 있었습니다. 알고보니 Postm..

Project/Distance 2025.03.11

[Distance] - 위치기반 매칭을 INDEX를 통해 개선해보자.

위의 화면은 사용자가 distance를 들어왔을 때 가장 먼저 볼 수 있는 화면이다.저 화면에 보이는 유저 4명은 총 3가지(비로그인 유저, 로그인한 유저, 로그인은 했지만 GPS추적을 거부한 사람)유형으로 구분하여 DB에서 불러오는 방식을 사용했다. 오늘 개선할 부분은 바로 로그인한 유저의 매칭 부분을 개선할 것입니다. public MatchResponseDto getNotFoundPositionMatchList(Member centerUser) { List userDtoList = memberReader.findMemberList().stream() ... .collect(Collectors.toList()); return getMatc..

Project/Distance 2025.02.25

[Distance] 짝퉁 카톡(KakaoTalk)을 만들어보자. - SSE

우리 서비스의 MVP기능을 뽑으라하면 위치기반을 통한 매칭과 채팅이라고 할 수 있다.우리가 원하는 채팅의 수준은 카카오톡과 비슷했다. 1. 1대1 채팅이 가능하여야 한다.2. 채팅방 내에서 사진을 보낼 수 있어야한다.3. 채팅방안에서 실시간으로 읽음표시가 사라져야 한다.4. 채팅 목록에서 실시간으로 메시지의 변화를 감지해서 보여주어야한다.총 이렇게 3가지였다. 다른 건 사실 크게 어렵지 않았고, 1, 2번은 굳이 없어도? 크게 불편하지 않았다. 하지만 3, 4번 같은 경우는 없으면 불편하고 사용자에게 버그처럼 느껴질 수도 있을 거 같았다. 우선 3번 같은 경우는 사용자가 방에 들어오면 Event를 감지하여서 Session Table에 값이 들어옴으로써 방에 있는지 없는지를 확인할 수 있었고, 덕분에 읽음..

Project/Distance 2024.10.29

[Distance] SQS를 도입해보자.

지금 프로젝트를 진행한지 어엿 반년이 지나고 800명의 유저와 3만건에 가까운 채팅을 많은 사용자들이 이용을 주었다..ㅎㅎ근데 가장 많이 들었던 아쉬운 점 중 하나가 "알림이 고장난거 아니에요?" 라는 피드백이었다. 왜 그럴까? 원래 초창기에 저희가 사용했던 알림 방식은 FCM을 통해서 채팅이 오면 바로 채팅내용을 카0오톡 처럼 바로 바로 보내주는 형식이었다.하지만 이렇게 하다보니 FCM자체가 동작을 안할 때가 있었고, 순서도 뒤죽박죽에 이미 갔던 문자알림이 또 가는 버그가 있었고, 무엇보다이렇게 했을 때 채팅하나 보내는데도 많은 쿼리가 나가는데 이에 FCM까지 전달하려고 하는게 아닌 거 같아 방식을 바꾸게 되었다. 그럼 어떻게 보냈냐?!특정 유저에게 메시지가 오면 FCM Table에 저장을 하고 스케줄..

Project/Distance 2024.10.24

[Distance] 나의 첫 서버 트래픽 경험기

구름톤에서 시작한 Distance프로젝트는 어느덧 순천향대, 경희대, 동국대, 서울여대, 한국외대를 지나 저희 팀의 리더분 학교인 전남대에도 배포를 하게 되었다. 저희가 이 프로젝트를 구현하고 순천향대에 첫 배포를 할 때 목표가 "서버를 터트릴때까지 해보자!" 였다.사실 ec2유형이 t2.micro여도 지금까진 단 한번도 서버가 터지지 않고 사용률이 70%이상만 가보기만 했다. 그리고 나름 채팅이 MVP이다보니 I/O가 많을 거 같아 미리 분산을 시켜두면서 나름 준비를 많이 해두었다.지금 현재 저는 판교에 있는 회사 인턴으로 하고 있는 중 2024/09/12에 전남대 단과대 축제에 맞춰 distance서비스를 배포를 하였다.오랜만에 배포라서 귀하디귀한(?) 점심시간도 자진 반납을 하고 서버 모니터링을 하..

Project/Distance 2024.09.18