피드로 돌아가기
The Node.js bug that's invisible to your monitoring
Dev.toDev.to
Backend

libuv Thread Pool Starvation으로 인한 p99 400ms 지연 분석 및 해결

The Node.js bug that's invisible to your monitoring

r9v2026년 6월 24일9advanced

Context

Node.js의 Event Loop 중심 모니터링 체계가 libuv Thread Pool의 병목 현상을 감지하지 못하는 가시성 공백 발생. 기본 4개로 제한된 Thread Pool 내에서 CPU-heavy 작업과 Blocking I/O가 경합하며 요청 지연이 가속화되는 구조적 한계 존재.

Technical Solution

  • Worker Threads 도입을 통한 인증 로직 분리로 bcrypt 연산과 libuv Pool 간의 자원 경합 제거
  • zlib.gzip 대신 Streaming API를 채택하여 단일 Slot 점유 시간을 단축하고 처리 효율 개선
  • getaddrinfo 기반의 dns.lookup을 c-ares 기반의 dns.resolve로 교체하여 Blocking syscall 제거
  • HTTP Agent에 DNS Cache Layer를 구축하여 외부 통신 시 발생하는 Thread Pool 요청 횟수 최소화
  • Hot Path 내 Filesystem 작업 배제 및 Stream 기반 처리로 Thread Slot 점유 시간 최적화

1. bcrypt 등 고비용 암호화 함수 사용 시 Worker Threads 분리 검토

2. 외부 API 호출 빈도가 높을 경우 dns.resolve 사용 및 DNS 캐싱 적용

3. 대용량 파일 처리 및 압축 시 Buffer 방식 대신 Stream API 우선 적용

4. p99 지표 상승 시 CPU/Memory 외에 Thread Pool 점유 가능성이 있는 모듈(fs, crypto, zlib, dns) 확인

원문 읽기