IT field notes/OpenTelemetry

OpenTelemetry 학습을 시작하며

게비의 필드노츠 2026. 8. 17. 19:20

최근 한 고객사의 관측성(Observability) 환경에서 마주한 제약을 풀기 위해 OpenTelemetry Collector를 검토한 적이 있다. 여러 계열사를 거느린 그룹사의 사례였는데, 통합 관제 플랫폼을 구축하는 과정에서 계열사 간 보안 문제로 관측성 플랫폼을 계열사별로 둘지, 아니면 통합 보안을 목표로 하나로 저장할지 고민하고 있었다.

이 고민은 둘 중 하나를 선택하면 되는 단순한 문제가 아니었다. 비용도, 관리 포인트도, 통합 관제라는 목적도 함께 얽혀 있어 상황에 맞는 적절한 대안이 필요했다. 또한 벤더가 제공하는 제약 - 하나의 수집기(Collector)에서는 하나의 소스로만 저장이 가능하다는 점 - 때문에 대안을 마련하기가 더욱 어려웠다.

그래서 검토한 것이 OpenTelemetry 기반 수집기다. 별도 개발 없이 제공되는 설정만으로, 하나의 통합 관제 테넌트에서 계열사별 소스를 각각 저장하고 관리하게끔 해주는 Processor, Exporter 등의 구성요소를 이미 포함하고 있었다.

간단하게 정리하면 다음과 같은 구조를 이용했다.

 

그림에서처럼, 소스 호스트에 설치된 OpenTelemetry Collector가 호스트에 쌓인 로그 파일을 수집한다. 이때 수집 단계에서 로그의 내용(JSON)을 읽어 그 안의 tenant 값을 속성으로 끌어올린다. 이렇게 붙은 tenant 속성을 기준으로, 라우팅(routing connector)이 로그를 계열사별 경로로 나누어 서로 다른 저장 위치로 내보낸다. 결국 하나의 테넌트에 여러 계열사의 로그를 모으되, 로그 스스로가 지닌 정보로 소속을 판별해 저장을 나누고, 각 계열사는 자신에게 허용된 영역에만 접근하도록 통제하는 구조다. 권한과 역할에 따라 데이터를 분리해 관리하는 것이다.

 

이는 다음과 같은 설정을 조정함으로써 가능하다.

# 핵심만 발췌 — 전체 설정은 다음 글에서 다룬다

receivers:
  filelog:
    include: [ /var/log/app/*.log ]
    operators:
      - type: json_parser         # ① 로그(JSON) 내용을 읽어
        parse_to: attributes      #    tenant 같은 값을 속성으로 올린다

connectors:
  routing:                        # ② 그 속성값에 따라 갈래를 나눈다
    table:
      - context: log
        condition: 'attributes["tenant"] == "team_a"'
        pipelines: [logs/team_a]
      - context: log
        condition: 'attributes["tenant"] == "team_b"'
        pipelines: [logs/team_b]

exporters:
  otlphttp/team_a:                # ③ 계열사별 저장 위치로 각각 보낸다
    endpoint: https://<A-엔드포인트>
  otlphttp/team_b:
    endpoint: https://<B-엔드포인트>

 

기본 기능만으로 소스의 내용을 읽고, 분기처리하여 각각의 소스 카테고리로 전송이 가능하다니 실로 그 당시에는 놀라웠다. 벤더의 기능으로 풀리지 않는 문제가 yaml 설정 몇 줄로 해결된 셈이다. 이러한 방식이라면 실제 다양한 기업의 고민 해결에도 표준을 적용할 방법을 정리해 놓는 것이 좋겠다는 결론에 이르렀다. 그래서 완성된 지식을 전달하기보다, 학습에 따른 결과를 정리하는 기록에 가깝다. 또한 OpenTelemetry에 흥미가 있는 사람들에게 조금이나마 도움이 되면 좋겠다.