pile·
아키텍처·마켓컬리마켓컬리 Hello World·

컬리에서 주문을 모니터링하는 법

복잡한 레거시 주문 조회를 운영 모니터링에 계속 사용하면서 발생한 느린 검색과 장애를 Kafka·Elasticsearch·Kibana 기반 이벤트 파이프라인으로 분리한 사례다. PHP 애플리케이션이 주문 이벤트를 Kafka에 비동기로 발행하고 ELK 대시보드가 실시간·누적 통계를 제공한다. 첫 배포 뒤 발견한 flush, ack, 정합성, 중복 문제까지 함께 다룬다.

핵심 포인트
  • 기존 조회는 7개 이상 테이블 조인, 4개 이상 서브쿼리, GROUP BY·HAVING·집계가 얽혀 주문이 몰리면 검색과 DB가 함께 느려졌다.
  • 주문 도메인 이벤트를 Kafka에 발행하고 Elasticsearch에 적재해 운영 조회 부하를 트랜잭션 DB에서 분리했다.
  • 서버별 파일 로그와 Filebeat 방식은 디스크·권한·배포 중 유실 위험이 있어 Kafka의 전달·내결함성을 택했다.
  • php-rdkafka의 produce는 비동기라 프로세스 종료 전에 flush하지 않으면 전송되지 않은 데이터가 유실될 수 있다.
  • 배포 뒤 ack 설정, 누락 이벤트의 DB 정합성 보완, 로그 ID 기반 멱등 처리가 추가로 필요했다.
상세 정리
  • 운영 요구: 24시간 주문과 새벽 배송을 지원하려면 주문 상태·처리 과정·상품·금액 통계를 실시간으로 확인해야 했다.
  • 레거시 증상: 주문량이 몰리면 주문서를 찾지 못하거나 시간 범위를 잘게 나눠 검색해야 했다. 데이터 정합성 문제로 특정 주문이 검색되지 않는 경우도 있었다.
  • 쿼리 병목: 다수 조인과 중첩 서브쿼리 위에 sum, count, distinct, GROUP BY, HAVING을 한 목록 조회에서 처리했다. 응답을 기다리는 동안 타임아웃과 DB 부하가 커졌다.
  • 코드 구조: 2천 줄이 넘는 비즈니스 로직과 뷰가 한 파일에 섞였고, 조건문으로 SQL 문자열을 조립해 튜닝과 변경이 어려웠다.
  • 전환 결정: 주문 도메인에서 이벤트가 생길 때마다 Kafka로 데이터를 보내고 기존 사내 ELK 플랫폼에서 Kibana 대시보드를 만들기로 했다.
  • 범위 절감: Kafka와 ELK 기반이 이미 있어 애플리케이션 연동, 이벤트 데이터 구조, 대시보드 구현에 집중할 수 있었다.
  • 파일 로그 비교: 각 인스턴스 파일과 Filebeat 방식은 disk full, 쓰기 권한 오류, 배포 중 파일 유실 가능성이 있었다. 서버 로컬 상태에서 전송 채널을 분리할 필요가 있었다.
  • 클라이언트: PHP 애플리케이션에는 php-rdkafka를 설치했다. Producer에 브로커를 등록하고 주문 payload를 Topic으로 produce했다.
  • 비동기 함정: 처음에는 produce 호출 뒤 전송 완료 전에 PHP 프로세스가 끝나는 패턴을 놓쳐 원인을 찾기 어려운 유실이 생겼다.
  • flush 적용: 미전송 메시지가 있으면 제한 시간 동안 flush해 전송을 마친 뒤 프로세스를 종료하도록 바꿨다.
  • 대시보드 결과: 실시간·누적 주문 건수와 금액, 주문 상품 통계를 Kibana에서 조회했고 접속 후 체감 약 1초 안에 결과를 볼 수 있었다.
  • 인프라 장애 식별: 첫 배포 약 일주일 뒤 특정 시간대 데이터가 사라졌고, 대시보드로 주문 시스템이 아니라 데이터 인프라 장애임을 확인했다.
  • 정합성 과제: 이벤트 수집이 하나라도 누락되면 DB의 현재 상태와 Elasticsearch 데이터가 달라졌다. 실시간 파이프라인 외 보정 경로가 필요했다.
  • 전달 보완: ack 옵션을 추가해 Kafka 전송 확인 수준을 명시했다. 속도와 허용 가능한 유실률에 맞춰 설정해야 한다.
  • 중복 대응: 같은 데이터가 여러 번 발생할 가능성을 고려해 로그 ID를 지정하고 소비·저장 과정에서 멱등성을 확보하려 했다.
왜 읽나레거시 트랜잭션 DB의 무거운 운영 조회를 이벤트 스트림과 검색 대시보드로 분리할 때 생기는 전달 보장과 정합성 과제를 함께 볼 수 있다.
마켓컬리
마켓컬리 Hello World 블로그
원문은 여기서 이어서 읽을 수 있어요
원문 읽기
읽음 (0)

이 글과 비슷한

  1. 아키텍처·dropbox-techDropbox Tech·

    Dropbox의 통합 콘텐츠 처리 플랫폼 Riviera, AI 시대로의 진화

    Dropbox가 파일 미리보기 생성용 내부 서비스로 출발한 콘텐츠 처리 플랫폼 Riviera가 약 10년에 걸쳐 Search·Replay·Sign·Dash가 공유하는 플랫폼으로, 나아가 AI 시대의 문서 처리 인프라로 진화한 과정을 다룬다. 미리보기를 '재사용 가능한 변환들의 조합'으로 재정의한 설계가 확장의 핵심이었고, 지금은 100개 넘는 변환 능력으로 초당 수십만 건을 처리한다. 최근엔 공개 API와 MCP로 외부 개발자에게도 열렸다.

  2. 아키텍처·github-engGitHub Engineering·

    AI 시대에 달라진 '예스'의 비용

    GitHub Engineering 에서 AI 코드 생성 도구가 보편화되면서 소프트웨어 엔지니어링 경제학이 어떻게 달라졌는지를 다룬다. 코드를 작성하는 비용은 낮아졌지만 그 코드를 소유하고 유지보수하는 비용은 그대로라는 점을 핵심 논지로, 엔지니어링 팀의 의사결정 방식도 달라져야 한다고 주장한다.

    #engineering-process#ai-code-generation#code-ownership+1
  3. 아키텍처·당근당근 테크블로그·

    천만 MAU를 지탱하는 커뮤니티 시스템 아키텍처

    당근 커뮤니티실이 2021년 약 100 RPS에서 현재 약 20,000 RPS를 처리하는 규모로 성장한 과정과, 이를 가능하게 한 "여러 웹앱 + 하나의 서버앱" 모듈형 모놀리스 아키텍처를 다룬다. 동네생활, 모임, 카페, 아파트 서비스를 소규모 팀이 장기 운영 가능한 구조로 설계한 원칙과, 장애 경험에서 도출한 resilience 패턴까지 단계별로 정리했다.

    #event-driven#kafka#postgres+2