LabHub
배우기 러닝패스 코스

Envoy 내부 구조 · 이름이 곧 인터페이스다 · 이론

대시보드가 통째로 빈 날

LabHub 에서 이어서 보기

한 줄 요약

Envoy 의 통계 이름은 문자열 하나에 여러 뜻이 들어 있는 구조다(cluster.<이름>.upstream_rq_total). 프로메테우스로 내보낼 때 그 문자열은 지표 이름과 라벨로 쪼개지고, 쪼개는 규칙은 직접 더할 수 있다. 그리고 이름은 곧 인터페이스라, 낱말 하나만 바꿔도 그것을 쓰던 대시보드가 빈다.

왜 이게 필요했나

프록시에서 무슨 일이 일어나는지는 로그로도 알 수 있지만, 로그는 요청마다 한 줄씩 쌓여서 "지금 전체가 어떤가" 를 묻기에는 비싸다. 통계는 그 반대다 — 요청 수만큼 늘지 않고, 처음부터 집계된 숫자로 들고 있다.

문제는 그 숫자가 오백 개가 넘는다는 것이다. 기본 설정에서도 그렇고, 클러스터가 늘면 클러스터마다 수십 개가 더 붙는다. 그래서 통계를 다루는 일은 "무엇이 있는지" 가 아니라 "필요한 것을 어떻게 찾고, 필요 없는 것을 어떻게 덜어내는가" 가 된다.

어떻게 동작하나

이름의 세 갈래. 이름의 첫 낱말이 무엇에 대한 숫자인지를 밝힌다.

| 접두사 | 무엇에 대한 숫자 | 대표 |
| --- | --- | --- |
| cluster.<이름>. | 업스트림 쪽 | upstream_rq_total, membership_healthy |
| http.<stat_prefix>. | 그 HTTP 연결 관리자가 처리한 요청 쪽 | downstream_rq_5xx |
| listener.<주소>. | 소켓 쪽 | downstream_cx_total |

같은 요청 하나가 세 군데에서 각각 세어진다. 그래서 세 숫자가 어긋나면 그 차이가 단서다 — 리스너에는 연결이 잡혔는데 http. 쪽 요청 수가 적으면 연결만 맺고 요청을 안 보낸 것이고, http. 쪽 5xx 는 늘었는데 cluster. 쪽 요청 수가 그대로면 업스트림까지 가지도 못한 것이다.

종류가 다르다. 카운터는 누적이라 늘기만 하고, 게이지는 지금 상태이며, 히스토그램은 분포다. 관리 포트의 /reset_counters 는 이름 그대로 카운터만 되돌린다. 게이지는 '지금 성한 서버가 몇 대인가' 같은 현재 상태라 되돌릴 것이 없다.

꺼내는 방법. /stats?filter=<정규식>?format=json 을 붙일 수 있고 둘은 함께 쓸 수 있다. 프로메테우스로 긁을 때는 /stats/prometheus 를 쓰는데, 여기서 이름이 쪼개진다. cluster.good.upstream_rq_total 은 지표 이름 하나와 클러스터 이름을 담은 라벨이 된다. 쪼개는 규칙은 Envoy 가 기본으로 여럿 들고 있고, stats_config.stats_tags 로 더할 수 있다 — 클러스터 이름에 팀 이름을 접두사로 붙여 두었다면 그것만 라벨로 뽑아 대시보드에서 팀별로 묶어 볼 수 있다.

덜어내는 방법. stats_config.stats_matcher 로 포함 목록이나 제외 목록을 둔다. 여기서 중요한 성질 하나 — 제외된 통계는 화면에서 숨겨지는 것이 아니라 아예 기록되지 않는다. 나중에 필요해져 되살려도 그 사이의 값은 없다.

현장에서 만나는 모습

대시보드가 통째로 빈 날. 누가 stat_prefix 를 더 읽기 좋은 이름으로 바꿨다. 트래픽에는 아무 영향이 없으니 배포는 조용히 지나갔고, 며칠 뒤 누가 "이 그래프 원래 이랬나요" 라고 묻는다. 값이 0 으로 떨어진 것이 아니라 시계열 자체가 사라진 것이라, '데이터 없음' 을 장애로 다루지 않는 알림은 울리지도 않았다. 이름은 인터페이스다 — 바꾸기 전에 쓰는 쪽을 먼저 찾는다.

시계열이 너무 많아진 경우. 클러스터가 수백 개인 프록시에서는 통계 수가 수만 개가 된다. 프로메테우스 쪽 저장 비용이 먼저 비명을 지르는데, 이때 손댈 곳은 수집 주기가 아니라 내보내는 목록이다.

히스토그램을 카운터처럼 읽는 경우. 요청 시간 같은 값은 평균 하나로 보면 거의 언제나 괜찮아 보인다. 느린 요청은 수가 적어서 평균을 거의 움직이지 않기 때문이다. 히스토그램은 그래서 있는 것이고, 보아야 할 것은 평균이 아니라 위쪽 백분위수다. 관리 포트의 텍스트 출력에는 백분위수가 함께 나오지만 기록된 값이 없으면 그렇게 표시되므로, 값이 없는 것과 0 인 것을 구분해 읽어야 한다.

"되돌렸는데 값이 안 바뀝니다." 게이지를 카운터로 착각한 것이다. 두 종류를 구분하는 습관이 있으면 이 질문 자체가 생기지 않는다.

공식 문서: [Statistics overview](https://www.envoyproxy.io/docs/envoy/v1.38.3/operations/stats_overview) · [Administration interface](https://www.envoyproxy.io/docs/envoy/v1.38.3/operations/admin)

다음 실습에서 할 것

같은 요청이 세 갈래 이름에서 각각 세어지는 것을 확인하고, filterformat=json 으로 필요한 것만 꺼내고, 프로메테우스 출력에서 이름이 어떻게 쪼개지는지 본다. 그다음 /reset_counters 가 카운터에만 듣는 것, 태그 규칙을 더해 라벨을 만드는 것, 제외 목록으로 통계를 덜어내는 것을 차례로 해 보고, 마지막에는 stat_prefix 한 낱말을 바꿔 옛 이름의 통계가 통째로 사라지는 것을 직접 본다.