Skip to content
isdnetworks
Go back

도착률 대비 처리량으로 잰다

(수정됨)

이미지 변환에서 90초 타임아웃이 나고 있었고 노드를 보니 nproc 8에 ps로 센 워커 프로세스가 십여 개 떠 있었다. queue:work 워커를 하나로 줄이면 웹이 여유를 얻지 않겠냐는 질문이 나왔다.

Table of contents

Open Table of contents

문제 — 프로세스 수로 낸 첫 답

내 첫 답은 십여 프로세스가 8코어를 경합하니 줄이면 나아진다는 것이었다. 프로세스 수만 보고 판단한 것이다.

지적이 하나 왔는데 도착률 대비 단일 워커 처리량이 결정 변수 아니냐는 것이었다. 프로세스를 줄이면 경합은 줄지만 처리량도 줄고 처리량이 도착률보다 낮으면 jobs 큐가 쌓인다.

검증 — 두 값의 실측

worker.log에서 두 가지를 뽑았다. 작업 시작 로그를 awk로 분 단위로 세니 도착률이 분당 수백 건이었다.

단일 워커 처리량은 started_at과 finished_at 차이의 분포로 냈다. 단독 실행일 때 2초 남짓이고 지금 경합 상태에서는 30초 안팎으로 십여 배 지연돼 있었다. 단독 기준으로 환산해도 워커 하나가 분당 30건 남짓이다.

판단 기준 — 숫자가 낸 결론

도착률이 분당 수백 건인데 단일 워커 처리량이 분당 30건 남짓이면 워커를 하나로 줄일 경우 분당 수백 건이 적체된다. php-fpm 굶음은 완화되지만 전체 입점사의 변환이 밀리는 과보정이다.

숫자를 놓고 보니 진짜 문제도 드러났다. 워커 개수가 문제가 아니라 단독 노드 하나에 전체 입점사의 변환 부하가 몰려 있어서 한 노드가 감당할 양이 아니었다. 답은 줄이는 것이 아니라 나누는 것이었다. 두 가지 방법이 있었는데 별도 노드로 분산하는 것과 이 노드를 카나리에서 해제해 부하 쏠림을 푸는 것이다. 뒤쪽을 골랐다. 이유는 노드 추가는 비용 승인이 필요한데 카나리 해제는 라우팅 가중치 하나라서다. 대신 카나리 검증을 그 기간 못 하는 것을 감수했다.

주의 — 조건이 바꾼 답

같은 세션 후반에 실제로 queue:work를 넷에서 하나로 줄였는데 모순이 아니라 조건이 바뀐 것이었다. 앞에서는 전체 변환이 비동기 jobs 큐로 들어와 도착률이 분당 수백 건이었다.

뒤에서는 변환이 동기 응답으로 이전되면서 큐는 잔여 부하만 받게 됐고 도착률이 확 떨어졌다. 그 상태에서는 워커 하나로 충분하므로 축소가 성립한다. 절대적인 워커 수는 없고 도착률에 따라 달라지며 도착률은 구조가 바뀌면 바뀐다.

교훈 — 적용 범위와 보이는 값

그래서 queue:work 수 판단은 항상 현재 비동기 도착률 대비 처리량으로 다시 재기로 하고 그 판단의 적용 범위도 함께 적었다. 전체 입점사 비동기 변환 큐를 단일 노드가 받는 상태라는 조건을 안 적으면 워커를 줄이면 안 된다는 문장만 규칙으로 굳는다.

내가 왜 틀렸는지도 남겨 뒀다. 프로세스 수는 ps 한 번이면 나오지만 도착률과 처리량은 worker.log를 파싱해야 나온다. 보이는 값으로 판단하고 싶어지는데 보이는 것이 결정 변수가 아니었고 무엇으로 판단할지를 먼저 정한 뒤 그것을 재야 했다.

정리


Share this post on:

Previous Post
매핑표를 먼저 완성한다
Next Post
링크 없음과 미응답의 구분