목차
promkr 뉴스레터 2025년 5월호
원문 정보
- 원문: Prometheus & Observability - 2025년 5월 소식
- 발행: 2025-05-03
이 호에 실린 소식 10개의 원문을 읽고 요약했습니다. 뉴스레터 설명이 아니라 링크가 가리키는 글의 내용을 기준으로 썼습니다. 한 해 전체의 흐름은 2025년 소식에 있습니다.
1. Prometheus 풀 방식의 선택 이유와 운영 조건
원문: Why is Prometheus Pull-Based? · mikkergimenez · 2022-12-26
Prometheus가 대상의 메트릭을 직접 가져오는 풀 방식을 택한 이유와 운영상의 장단점을 살펴본 글입니다. 저자는 SNMP, JMX, Nagios도 풀 방식을 사용한다고 짚습니다. 글에서 인용한 Prometheus FAQ는 풀 방식이 푸시보다 조금 낫다는 입장이지만, 모니터링 시스템을 고르는 주요 기준으로 삼지는 말라고 설명합니다. 수집 방식의 차이는 대상의 생존 여부를 판단하고 장애 원인을 추적할 때 의미가 있습니다.
HTTP로 메트릭을 가져오면 필요할 때 별도 모니터링 인스턴스를 띄우거나 브라우저로 대상 상태를 직접 살펴볼 수 있습니다. 수집 주기도 중앙에서 바꿀 수 있어 애플리케이션 변경을 기다릴 필요가 없습니다. 저자는 잘못 설정한 에이전트가 데이터를 지나치게 보내 수집 서버에 과부하를 일으킬 가능성도 낮다고 설명합니다. 수집 대상 목록을 알고 있어야 한다는 조건은 장애로 사라진 대상과 의도적으로 제거한 대상을 구별하는 데 도움이 됩니다.
풀 방식에서는 서비스 검색과 엔드포인트 접근성이 필요합니다. 저자는 Kubernetes, EC2 API, 정적 설정을 대상 검색 수단으로 들며, 수십만 개 메트릭을 내보내는 exporter에서는 HTTP 타임아웃이 문제가 될 수 있다고 적었습니다. 수집 서버가 멈춘 동안에는 데이터를 잃지만, 애플리케이션이 재전송용 데이터를 보관할 필요는 없습니다. Pushgateway를 사용해도 마지막 수집 단계는 풀 방식입니다. Pushgateway는 Prometheus에 이벤트를 밀어 넣지 않고 스크랩할 엔드포인트를 제공하며, 글은 특정 머신이나 작업 인스턴스에 종속되지 않는 서비스 수준 배치 작업의 결과 수집을 일반적인 용도로 소개합니다.
2. 중복 수집과 미사용 메트릭 제거로 줄인 메모리
원문: Prometheus: How We Slashed Memory Usage · Aleksandro Matejic · 2025-04-06
Aleksandro Matejic은 Kubernetes 클러스터에서 Prometheus 메모리 사용량이 55 GB를 넘어 최대 60 GB에 이른 문제를 조사했습니다. OOMKilled 재시작과 PromQL 쿼리 실패가 반복됐고, Prometheus가 동작하지 않는 동안 스크랩도 빠졌습니다. 저자는 활성 시리즈 수와 메트릭별 시리즈 수를 PromQL로 확인하고, promtool tsdb analyze로 TSDB 블록의 메트릭과 레이블 카디널리티를 분석했습니다. 분석한 블록에는 시리즈 3,769,527개가 있었습니다.
큰 비중을 차지한 데이터는 NGINX Ingress의 히스토그램 메트릭이었습니다. nginx_ingress_controller_request_duration_seconds_bucket은 해당 블록에서 시리즈 533,292개를 차지했습니다. 여기에 ServiceMonitor와 kubernetes-pods 작업이 같은 ingress-nginx 메트릭을 각각 수집하는 문제가 겹쳤습니다. 메트릭 내용이 같아도 job이나 instance 레이블이 다르면 별도 시리즈가 되므로 수집량이 늘어났습니다.
저자는 ingress-nginx 네임스페이스를 Pod 단위 수집에서 제외하고 ServiceMonitor 수집을 유지했습니다. Grafana 대시보드와 알림에서 쓰지 않는 메트릭도 제거했습니다. path, replicaset, controller_revision_hash, owner_name에는 labeldrop을 적용했습니다. 이때 레이블 제거만으로 서로 다른 시리즈가 동일해지면 중복 시리즈 충돌과 수집 오류가 발생한다는 조건을 명시합니다. 사용 여부를 확인하기 위해 대시보드와 알림의 PromQL을 추출하는 스크립트, 그 결과와 고카디널리티 메트릭을 대조하는 스크립트도 공개했습니다.
저자가 보고한 변경 후 메모리 사용량은 거의 60 GB에서 18–25 GB로 줄었고, 활성 시리즈 수는 약 1,000만 개에서 400만 개 미만으로 내려갔습니다. 글의 마지막에는 전체 절감 효과를 약 50%로 표현하며 주요 기능 손실은 겪지 않았다고 밝혔습니다. 이 사례의 제거 기준은 카디널리티 자체가 아니라 실제 사용 여부였습니다. 대시보드와 알림 필터에 필요한 레이블은 유지했습니다.
3. GreptimeDB v0.13의 Prometheus 장기 저장 실험
원문: GreptimeDB as Prometheus Long-term Storage · Anarcher’s Trashcan · 2025-04-13
저자는 GreptimeDB v0.13을 간단히 구성해 Prometheus 장기 저장소로 사용할 수 있는지 조사했습니다. GreptimeDB는 메트릭, 로그, 이벤트를 다루는 시계열 데이터베이스입니다. 글은 SQL 지원, Parquet 기반 컬럼 저장, 클라우드 객체 저장소를 바탕으로 한 컴퓨팅과 저장 분리, 선택적인 인덱스 설정을 특징으로 소개합니다. Prometheus의 레이블과 값 중심 모델과 달리 테이블 안에 Tags, Fields, Timestamps를 두며, 여러 Prometheus 메트릭을 물리 테이블로 묶습니다.
클러스터에서 Metasrv는 데이터베이스와 테이블, 데이터 분산 및 요청 경로 정보를 관리합니다. Frontend는 수집·쿼리 프로토콜을 받아 Datanode로 요청을 전달하고, Datanode는 테이블의 region을 관리하며 읽기와 쓰기를 처리합니다. Frontend는 Prometheus remote write와 Prometheus HTTP API를 지원합니다. 저자는 수집과 쿼리의 부하 성격이 다르므로 Frontend를 읽기 전용과 쓰기 전용으로 나누는 구성이 적절하다고 보았습니다.
실험에서는 각 Kubernetes 클러스터의 Prometheus가 remote write로 보낸 메트릭이 여러 Datanode에 분산되지 않고 한 노드에 모였습니다. 메트릭용 물리 테이블이 하나였고, 그 테이블의 모든 logical region을 한 Datanode가 맡았기 때문입니다. 부하를 나누려면 테이블을 파티셔닝해야 했지만, 저자가 확인한 범위에서는 job 레이블을 해시해 고르게 분할하는 방법이 아직 없었습니다. 해당 노드가 재시작하거나 상태가 나빠지면 모든 메트릭을 읽지 못하는 문제도 확인했습니다. 읽기를 분산할 follower peer 기능은 당시 제공되지 않았고 enterprise edition에서 활성화할 계획으로 소개됐습니다.
저자는 이 실험에서 읽기와 쓰기 계층의 분리, 최근 데이터와 장기 데이터 처리의 분리 필요성을 도출했습니다. 고카디널리티 레이블은 역색인 저장과 검색 비용을 키우므로 scanning+pruning 방식이 효과적일 수 있고, 인덱스와 함께 사용하는 접근이 더 나을 수 있다는 관점도 제시합니다.
4. GitHub Actions 워크플로의 CPU 프로파일링
원문: Introducing Profiling GitHub Actions · Frederic Branczyk · 2025-04-23
Polar Signals가 GitHub Actions 워크플로 전체의 On-CPU와 Off-CPU 프로파일링 데이터를 수집하는 Action을 공개했습니다. 벤치마크 실행을 분석하거나 CI/CD 파이프라인에서 시간이 어디에 쓰이는지 파악해 처리 시간을 줄이는 용도입니다. 기반은 Polar Signals Agent이며, 회사는 여러 언어를 지원하고 별도 계측 없이 1% 미만의 오버헤드로 사용할 수 있다고 설명합니다. 워크플로에는 Action 단계 하나를 추가하면 됩니다.
설정에는 Polar Signals Cloud API 토큰과 프로젝트 UUID가 필요합니다. 토큰을 저장소의 GitHub Actions secret으로 등록한 뒤 워크플로 앞부분에서 Action을 실행합니다. 원문의 예제는 polarsignals/gh-actions-ps-profiling@v0.4.0을 사용하고, polarsignals_cloud_token과 project_uuid를 전달합니다. 프로젝트 UUID는 민감한 값이 아니며 배포 링크에도 포함되므로 secret으로 만들 필요가 없다고 안내합니다.
연동 후에는 각 pull request에 프로파일링 데이터의 배포 링크가 자동으로 게시됩니다. 사용자는 링크를 열어 Polar Signals Cloud에서 해당 실행의 프로파일을 확인할 수 있습니다. 링크 생성에는 deployments: write 권한이 필요합니다. 글에서 소개한 구성은 Cloud로 데이터를 보내고 조회하는 흐름이며, 서비스 체험 기간은 14일로 안내돼 있습니다.
5. SSH로 원격 로그를 조회하는 Nerdlog
원문: Nerdlog · dimonomid
Nerdlog는 여러 원격 호스트의 로그를 시간 범위와 패턴으로 검색하고 타임라인 히스토그램을 표시하는 TUI 로그 뷰어입니다. README는 여러 Linux 인스턴스에서 systemd 서비스로 실행하던 웹 서비스의 로그를 효율적으로 읽으려는 필요에서 출발했다고 설명합니다. 주된 입력은 /var/log/messages, /var/log/syslog, journalctl이며, 프로젝트는 1 GB 이상의 큰 로그 파일도 효율적으로 다룬다고 소개합니다.
중앙 수집 서버를 두는 대신 대상 노드마다 SSH 연결을 유지합니다. 로그 분석은 원격 노드에서 실행하며, 파일 전체를 로컬로 가져오지 않습니다. 쿼리마다 각 logstream에서 기본 최대 250개 메시지와 히스토그램 데이터를 받고, 여러 노드의 응답을 합쳐 표시합니다. 메시지 수는 설정으로 바꿀 수 있고 다음 묶음을 페이지 단위로 읽을 수 있습니다. 전송 데이터 대부분에는 gzip을 적용합니다. 원격 셸 연결 명령을 바꿀 수 있어 Teleport 같은 도구도 사용할 수 있습니다.
조회 화면에서는 Awk 패턴으로 조건을 지정하고 히스토그램에서 시간 범위를 선택합니다. SSH 설정 파일의 호스트·사용자·포트를 읽으며 호스트 이름에 glob 패턴도 지원합니다. 별도 YAML 파일에는 사용자 지정 로그 경로를 등록할 수 있습니다. 현재 쿼리를 다시 여는 명령 문자열을 복사해 공유하거나, 불러온 로그를 파일로 저장하는 기능도 제공합니다. 탐색에는 일반 키보드 조작과 Vim 방식 단축키를 사용할 수 있습니다.
원격 호스트에는 SSH 접근 권한과 GNU awk인 gawk가 필요하며 mawk로 대체할 수 없습니다. 파일 기반 logstream은 현재 연속된 로그 파일을 최대 2개까지 묶을 수 있습니다. Windows에서는 클라이언트만 실행할 수 있고 Windows 호스트의 로그 수집은 지원하지 않습니다. README는 기본적으로 로그 파일을 먼저 찾고, 파일이 없을 때 journalctl을 사용한다고 설명합니다.
6. YAML로 생성하는 Stactus 상태 페이지
원문: Stactus · slok
Stactus는 YAML 설정과 인시던트 기록으로 정적 상태 페이지를 만드는 도구입니다. 작성자는 상태 페이지의 목적을 고객에게 서비스 상태와 진행 상황을 알리는 소통으로 봅니다. 지연 시간 측정이나 내부 메트릭 수집을 담당하는 복잡한 백엔드를 상태 페이지에 요구하지 않습니다. 단일 바이너리가 HTML을 생성하므로 결과물을 GitHub Pages에 올리거나 Nginx로 제공할 수 있습니다.
설정은 페이지 이름·URL·테마·시스템 목록을 담은 일반 설정 파일과 인시던트별 YAML 파일로 나뉩니다. 인시던트에는 영향을 받는 시스템, 영향도, 시간순 업데이트를 기록합니다. 업데이트는 시각과 설명을 포함하며, investigating: true는 조사 중인 상태를, resolved: true는 해결 상태를 나타냅니다. 둘 다 없으면 일반 업데이트로 취급합니다. 설명에는 Markdown을 사용할 수 있고, 시각에는 RFC3339 외에 이전 업데이트 기준 +17m 같은 상대 표기도 지원합니다. 시간대를 생략하면 UTC를 적용합니다.
stactus serve는 개발 서버에서 페이지를 생성해 보여주고, stactus generate는 배포할 정적 파일을 만듭니다. 구독용 Atom 피드와 Prometheus 메트릭도 정적 생성 결과에 포함됩니다. 메트릭은 전체 상태, 시스템별 진행 중인 인시던트와 영향도, MTTR을 나타냅니다. 사용자는 이 공개 메트릭을 수집해 상태 변경 알림을 구성할 수 있습니다.
기본 simple 테마는 인시던트 상세 페이지, 이력 페이지의 페이지 나누기, 첫 화면의 진행 중인 인시던트 표시를 제공합니다. 사용자 정의는 현재 테마 자체가 아니라 템플릿 변경을 지원합니다. Go HTML template과 sprig 확장을 사용하며, 템플릿과 정적 자산을 별도 디렉터리에 둡니다. Atlassian status page의 공개 API에서 데이터를 가져와 Stactus YAML로 옮기는 마이그레이션 기능도 있습니다.
7. 단일 컨테이너로 운영하는 Telebugs 오류 추적
원문: Self-hosted error tracking · Telebugs
Telebugs는 자체 서버에 설치하는 오류 추적 제품으로, 기존 Sentry SDK를 유지하면서 보고 대상 DSN을 Telebugs 서버로 바꾸는 방식을 제공합니다. 제품 페이지는 오류 수집·그룹화·알림에 범위를 집중해 운영할 소프트웨어를 줄였다고 설명합니다. 관련 오류 보고를 묶고 발생량이 많은 문제를 앞에 표시하며, 해결한 오류가 다시 발생하면 다시 열고 팀에 알립니다.
오류 화면에는 backtrace, breadcrumbs, 요청 정보, 지역 변수, 사용자 정의 문맥을 함께 제공합니다. 알림 채널은 push, 이메일, Slack, Discord, Teams, webhook이며 알림 규칙으로 소음을 조절합니다. 허용한 AI 코딩 에이전트가 MCP로 보고서를 확인하는 기능도 소개합니다. 제품은 Sentry의 성능 모니터링, 로그, session replay, 코드 커버리지 등 더 넓은 옵저버빌리티 기능을 대체하지 않는다고 명시합니다.
Telebugs는 Ruby on Rails로 만들었으며 SQLite가 애플리케이션 데이터, 캐시, 백그라운드 작업을 담당합니다. 별도 PostgreSQL, Redis, 큐 브로커 없이 Docker 컨테이너 하나로 실행하고 영속 볼륨 하나를 백업합니다. AMD64와 ARM64를 지원하며 설치 최소 사양은 RAM 1 GB와 CPU 1코어입니다. 업체는 2 vCPU와 RAM 4 GB에서 완전히 처리한 보고서를 초당 약 50개, 하루 약 430만 개 처리한다고 밝힙니다.
CLI는 설치, 상태 확인, 업데이트, 이전 버전 복귀, 백업과 복원을 관리합니다. 라이선스가 적용된 도메인의 인스턴스 하나에 프로젝트와 팀원을 제한 없이 둘 수 있습니다. 같은 주 버전의 업데이트는 무료지만 향후 주 버전은 별도 유료 업그레이드가 될 수 있습니다. 설치와 라이선스 영수증 이전을 마친 뒤 애플리케이션과 사용자가 인스턴스에 접근할 수 있으면 외부 인터넷 없이 기본 오류 추적을 실행할 수 있습니다. 초기 다운로드, 업데이트, 외부 알림에는 네트워크나 파일 전달 경로가 필요합니다.
8. 맞춤형 OpenTelemetry Collector 배포판 빌드 자동화
원문: OpenTelemetry Distribution Builder · observIQ
OpenTelemetry Distribution Builder는 필요한 Collector 구성 요소를 manifest.yaml로 정의하고 여러 플랫폼의 바이너리와 설치 패키지를 만드는 도구입니다. 내부에서는 OpenTelemetry Collector Builder인 OCB를 사용합니다. README는 단일 Collector 바이너리 생성에 초점을 둔 OCB 위에 패키징과 GitHub 버전 릴리스 관리를 더했다고 설명합니다. 실행 경로로 호스트 CLI, Docker, Google Cloud Build, GitHub Action을 제공합니다.
매니페스트에는 배포판 정보와 extensions, exporters, processors, receivers, connectors, providers를 지정합니다. 이미 사용하는 Collector 설정이 있으면 --from-config로 필요한 구성 요소의 매니페스트를 만들 수 있습니다. --generate-only를 붙이면 빌드 없이 매니페스트만 생성합니다. 생성 매니페스트에는 기본적으로 Bindplane 구성 요소가 포함되며 --no-bindplane으로 제외할 수 있습니다. 호스트 CLI는 전체 빌드에 필요한 OCB와 Go를 자동으로 내려받으므로 Docker가 필수는 아닙니다.
빌드 대상은 --platforms에 운영체제와 아키텍처 조합으로 지정합니다. README는 Linux와 Darwin, amd64와 arm64 조합을 예로 듭니다. 결과물에는 APK·DEB·RPM 패키지, TAR.GZ, 원시 바이너리, 소스 묶음, SBOM, 체크섬, 빌드 메타데이터가 포함됩니다. GitHub Actions 예제는 observiq/otel-distro-builder@v1.1.0으로 빌드한 뒤 별도 릴리스 단계에서 산출물을 첨부합니다. 릴리스 생성과 변경에는 contents: write 권한을 설정합니다.
병렬 빌드 작업 수는 --parallelism으로 조절하며 기본값은 4입니다. 프로젝트는 병렬도를 낮추면 최대 메모리 사용량이 줄지만 빌드 시간이 길어질 수 있다고 설명합니다. 높은 병렬도는 메모리가 충분할 때 시간을 줄일 수 있으나 메모리 부족 오류를 일으킬 수 있습니다. 구성 요소가 많은 Collector 빌드에는 호스트나 Docker에 최소 4–6 GB RAM을 확보하고, 더 크거나 병렬 작업이 많은 빌드에는 추가 메모리가 필요하다고 안내합니다.
9. dish의 HTTP·TCP 헬스체크
원문: dish (formerly savla-dish)
원문 페이지를 받지 못해 뉴스레터 소개만 옮깁니다. dish는 HTTP와 TCP 엔드포인트의 헬스체크를 수행하는 가벼운 모니터링 도구이며, 뉴스레터는 blackbox_exporter와 같은 개념을 다른 방식으로 구현한 도구로 소개합니다.
10. Perses의 대시보드 코드 관리와 임베딩
원문: Perses · Perses
Perses는 옵저버빌리티 데이터를 표시하는 대시보드 도구이자 도구 간 상호운용성을 위한 공개 대시보드 명세를 만드는 프로젝트입니다. 홈페이지는 Prometheus 메트릭, Tempo 트레이스, Loki 로그, Pyroscope 프로파일 지원을 소개합니다. Prometheus용 메트릭 탐색기와 PromQL 디버거를 제공하고, Tempo 데이터는 산점도·Gantt 차트·표로 표시합니다. Pyroscope 프로파일은 대화형 flame graph로 볼 수 있습니다. 모든 구성 요소는 Apache 2.0 라이선스로 공개되며 CNCF sandbox 프로젝트에 속합니다.
대시보드는 제공하는 SDK로 코드로 작성할 수 있습니다. 색상부터 복잡한 템플릿까지 라이브러리로 정의해 여러 대시보드에서 재사용하는 방식입니다. 대시보드 형식의 정적 검증과 사용자 정의 lint 규칙을 지원하고, CLI인 percli로 CI/CD 파이프라인 작업을 실행할 수 있습니다. 전체 애플리케이션을 실행하지 않고 npm 패키지의 패널이나 대시보드 구성 요소를 다른 UI에 넣는 방식도 제공합니다.
Kubernetes에서는 Perses operator가 인스턴스와 대시보드를 Custom Resource로 선언해 관리하므로 GitOps 흐름에 연결할 수 있습니다. 데이터 소스 검색은 HTTP 서비스나 Kubernetes API에서 대상을 찾아 자동 등록합니다. 데이터 소스와 변수의 범위는 global, project, dashboard로 나뉘며, 더 좁은 범위의 설정이 상위 범위를 덮어씁니다. 공통 설정을 공유하면서 개별 대시보드에 필요한 값을 따로 지정할 수 있습니다.
접근 제어에는 자체 사용자 관리와 외부 OIDC/OAuth 연동을 제공하고, 역할과 역할 바인딩을 사용하는 RBAC로 프로젝트 및 전역 자원 권한을 관리합니다. 기존 Grafana 대시보드는 웹 UI에서 JSON을 가져오거나 percli로 일괄 이전할 수 있습니다. 홈페이지는 이 변환을 best-effort 방식으로 명시하므로 모든 정의의 완전한 변환을 보장하지는 않습니다.