Datadog

186 개의 포스트

www.datadoghq.com/blog/engineering

태그로 필터

datadog

대규모 스테가노그래피: Datadog 위젯 스크린샷에 공유 URL 임베딩하기 (새 탭에서 열림)

Datadog은 사용자가 대시보드 위젯을 스크린샷으로 캡처할 때 유실되는 쿼리, 시간 범위 등의 컨텍스트를 보존하기 위해 픽셀 수준의 보이지 않는 워터마크 기술을 도입했습니다. 위젯의 테두리 픽셀에 미세한 색상 변화를 주어 메타데이터 키를 인코딩함으로써, 정적 이미지에서도 원본 데이터와 상호작용할 수 있는 기능을 구현했습니다. 이 시스템은 하루 10억 개 이상의 위젯 렌더링을 처리하면서도 사용자 경험에 영향을 주지 않는 성능과 투명성을 유지합니다. ### 스크린샷의 한계와 보이지 않는 워터마크의 필요성 - 대시보드 공유 링크는 실시간 데이터와 쿼리 정보를 포함하지만, 많은 사용자는 여전히 직관적이고 권한 문제에서 자유로운 스크린샷 공유를 선호합니다. - 일반적인 스크린샷은 이미지 픽셀 정보만 남기 때문에, 당시의 구체적인 타임프레임이나 기반 쿼리, 대시보드 상태와 같은 중요한 컨텍스트가 모두 사라집니다. - Datadog은 사용자 인터페이스를 해치지 않으면서도 스크린샷 내부에 보이지 않게 메타데이터를 심어, 이미지를 다시 Datadog이나 협업 도구(Slack 등)에 붙여넣었을 때 원본 위젯을 복구하고자 했습니다. ### 효율적인 데이터 관리를 위한 Redis 캐싱 전략 - 위젯 정의(Definition) 데이터는 평균 2kB로 이미지에 직접 모두 인코딩하기에는 너무 큽니다. - 이를 해결하기 위해 전체 위젯 정의는 Redis 캐시에 저장하고, 이를 식별할 수 있는 짧은 8바이트 고유 키(Snapshot ID)만 워터마크로 인코딩합니다. - 하루 10억 건 이상의 위젯 렌더링과 초당 35,000건의 피크 타임을 감안하여, 충돌 방지를 위해 조직 ID(Org ID)를 조합한 키 구조를 사용하며 데이터는 1시간 동안 유지됩니다. - 지연 시간을 최소화하기 위해 프론트엔드에서 낙관적(Optimistic)으로 ID를 생성하여 렌더링 즉시 워터마크를 적용합니다. ### 픽셀 단위의 RGB 인코딩 메커니즘 - 모든 위젯에 공통적으로 존재하는 1픽셀 두께의 테두리(Border)를 데이터 삽입 위치로 선정하여 시각적 일관성을 유지합니다. - 워터마크는 총 10개의 픽셀로 구성됩니다. 시작과 끝을 알리는 2개의 센티널(Sentinel) 픽셀과 그 사이의 8개 데이터 픽셀이 배치됩니다. - 각 데이터 픽셀은 1바이트(8비트)를 저장하며, RGB 채널에 비트를 분산(R: 3비트, G: 3비트, B: 2비트)하여 저장합니다. - 기본 색상에서 채널별로 아주 미세한 오프셋(최대 +7)만 조정하기 때문에 육안으로는 원본 테두리 색상과 구분이 불가능합니다. 이 기술은 대규모 트래픽 환경에서도 성능 저하 없이 정적 이미지에 생명력을 불어넣는 창의적인 엔지니어링 사례입니다. 협업 과정에서 스크린샷을 자주 활용하는 팀이라면, Datadog의 이러한 기능을 통해 이미지 너머의 원본 지표와 쿼리를 즉시 추적하여 문제 해결 속도를 높일 수 있습니다.

datadog

Steganography at scale: Embedding share URLs in Datadog widget screenshots (새 탭에서 열림)

데이터독(Datadog)은 사용자가 위젯을 스크린샷으로 캡처하더라도 쿼리, 시간 범위, 대시보드 설정과 같은 풍부한 컨텍스트를 보존할 수 있도록 픽셀 단위의 '보이지 않는 워터마크' 시스템을 구축했습니다. 위젯의 메타데이터 전체를 이미지에 직접 담는 대신, 해당 데이터를 저장한 Redis 캐시의 고유 키를 위젯 테두리 픽셀의 RGB 값을 미세하게 조정하여 인코딩하는 방식을 채택했습니다. 이를 통해 사용자 경험을 해치지 않으면서도 하루 10억 개 이상의 위젯에 대해 스크린샷만으로 원본 데이터에 접근할 수 있는 연결성을 제공합니다. **스크린샷의 한계와 워터마킹의 도입 배경** - 대시보드 위젯을 복사하여 붙여넣으면 라이브 프리뷰와 데이터 연결이 유지되지만, 많은 사용자는 직관적이고 권한 문제에서 자유로운 스크린샷 방식을 선호합니다. - 하지만 일반적인 스크린샷은 캡처 시점의 쿼리, 시간 범위, 시각화 유형 등 유용한 메타데이터를 모두 잃어버린다는 단점이 있습니다. - UI에 요소를 추가하지 않고도 이 정보를 보존하기 위해, 육안으로는 식별할 수 없지만 알고리즘으로 읽을 수 있는 픽셀 기반 워터마킹 기술을 도입했습니다. **데이터 최적화 및 캐싱 전략** - 위젯 정의 데이터는 평균 2KB로 이미지에 직접 인코딩하기에는 너무 크기 때문에, 전체 데이터는 Redis 캐시에 저장하고 이를 참조하는 짧은 고유 ID만 워터마크에 포함합니다. - 위젯이 렌더링될 때마다 프론트엔드에서 낙관적(Optimistic)으로 ID를 생성하여 백엔드 응답을 기다리지 않고 즉시 워터마크를 삽입함으로써 성능 저하를 방지합니다. - 조직 ID와 8바이트 무작위 ID를 조합하여 대규모 환경에서도 ID 충돌 가능성을 극도로 낮추었으며, 데이터는 스크린샷이 주로 활용되는 시간대를 고려해 1시간 동안 캐싱됩니다. **픽셀 레벨의 미세 인코딩 기법** - 모든 대시보드 위젯이 공통적으로 가진 1px 두께의 테두리를 데이터 삽입 공간으로 활용하여 시각화 유형에 상관없이 일관된 적용이 가능하게 했습니다. - RGB 모델의 각 채널 값을 미세하게 오프셋(Offset)하는 방식을 사용합니다. 기본 배경색에서 각 채널값을 조정한 뒤 0~7 사이의 값을 더해 픽셀당 약 9비트의 데이터를 저장합니다. - 워터마크의 시작과 끝을 알리는 센티널(Sentinel) 픽셀을 배치하고 그 사이에 8개의 데이터 픽셀을 넣어 총 8바이트의 ID를 인코딩하며, 이는 육안으로 거의 식별되지 않습니다. 이 시스템은 장애 대응이나 협업 과정에서 스크린샷이라는 익숙한 도구를 사용하면서도, 필요할 때 언제든 원본 데이터 컨텍스트로 복귀할 수 있는 강력한 연결성을 제공합니다. 대규모 트래픽 환경에서도 성능 영향 없이 작동하도록 설계된 이 기법은 단순한 이미지를 지능적인 데이터 포인터로 변환하는 실용적인 해법을 제시합니다.

datadog

대규모 자율형 SRE 에이전트를 위한 실환경 평가 플랫폼 구축 방법 (새 탭에서 열림)

Datadog은 자율형 사고 조사 에이전트인 'Bits AI SRE'를 개발하면서, 특정 기능을 개선했을 때 다른 영역에서 예상치 못한 성능 저하(Regression)가 발생하는 문제를 겪었습니다. 이를 해결하기 위해 실제 운영 환경의 사고 맥락을 재현하고 에이전트의 추론 과정을 일관되게 측정할 수 있는 '재현 가능한 평가 플랫폼'을 자체 구축했습니다. 이 플랫폼은 프로덕션 환경의 복잡한 신호를 오프라인에서 재실행 가능한 환경으로 변환함으로써, 에이전트의 품질을 데이터에 기반해 지속적으로 개선할 수 있게 해줍니다. **기존 테스트 방식의 한계와 회귀 문제** * 단순한 단위 테스트나 개별 도구(Tool) 레벨의 테스트는 에이전트가 여러 도구를 체이닝(Chaining)하며 추론하는 복합적인 과정을 검증하는 데 한계가 있었습니다. * 특정 모니터에서 서비스 이름을 추출하는 등의 기능 개선이 실제로는 불필요한 노이즈를 유발하여, 오히려 에이전트의 전체적인 추론 품질을 떨어뜨리는 사례가 발생했습니다. * 실시간 운영 환경에서의 재실행(Live Replay)은 데이터의 만료, 환경의 가변성, 결과 집계의 어려움으로 인해 대규모 평가에 적합하지 않았습니다. **재현 가능한 평가를 위한 '레이블'의 구조** * 플랫폼의 핵심인 '레이블'은 근본 원인을 정의하는 '정답(Ground Truth)'과 사고 당시의 신호를 담은 '월드 스냅샷(World-snapshot)'으로 구성됩니다. * 월드 스냅샷은 원시 데이터를 그대로 저장하는 대신 에이전트가 당시 사용할 수 있었던 텔레메트리 쿼리(지표, 로그, 배포 이벤트 등) 정보를 보존하여 실제 제약 사항을 재현합니다. * Kubernetes 파드 실패부터 Kafka 지연까지, 실제 SRE가 직면하는 다양한 장애 모드와 기술 스택을 포괄하는 광범위한 레이블 세트를 구축하여 평가의 객관성을 확보했습니다. **레이블 생성 및 검증의 자동화 (Agentic Validation)** * 초기 수동 레이블링의 한계를 극복하기 위해, 사용자의 피드백과 Bits AI의 자체 조사 데이터를 결합하여 레이블을 자동 생성하는 파이프라인을 구축했습니다. * 레이블의 양이 급증함에 따라 발생하는 품질 저하 문제를 해결하기 위해, 에이전트가 직접 모호한 신호를 정리하고 관계를 도출하는 '에이전트 기반 검증' 단계를 도입했습니다. * 이 시스템을 통해 레이블 생성 속도를 10배 이상 향상시켰으며, 사람이 최종 검토하기 전 데이터의 정밀도를 높여 평가 신뢰도를 강화했습니다. **대규모 평가 오케스트레이션과 성능 추적** * 다양한 모델 버전과 설정 변경 사항이 기존의 Kafka나 Kubernetes 조사 품질에 영향을 주지 않는지 확인하기 위해 대규모 병렬 평가 시스템을 운영합니다. * 레이블 세트를 세부 카테고리별로 분할(Segmentation)하여 관리함으로써, 어떤 변경이 특정 시나리오에 어떤 영향을 주는지 정밀하게 분석할 수 있습니다. * 모든 평가 결과는 지표화되어 시간에 따른 성능 추이를 추적하고, 버전 간 비교를 용이하게 하여 새로운 기능 배포에 대한 확신을 제공합니다. 복잡한 추론을 수행하는 AI 에이전트 개발 시, 단순히 개별 도구의 정확도에 의존하기보다 실제 운영 데이터의 '쿼리 가능성'과 '맥락'을 보존하는 오프라인 평가 환경을 구축하는 것이 필수적입니다. 이는 사용자 피드백을 제품 개선의 선순환으로 연결하는 핵심 인프라가 됩니다.

datadog

업서트가 업데이트하지 않아도 쓰기가 발생하는 경우: 대규모 Postgres 성능 디버깅 (새 탭에서 열림)

데이터독(Datadog)은 수백만 개의 일시적인 호스트 메타데이터를 효율적으로 관리하기 위해 새로운 업서트(Upsert) 쿼리를 도입했으나, 예상과 달리 디스크 쓰기와 WAL(Write-Ahead Logging) 동기화가 급증하는 문제에 직면했습니다. 조사 결과, PostgreSQL의 `ON CONFLICT DO UPDATE` 구문은 `WHERE` 조건에 의해 실제 업데이트가 수행되지 않더라도 행 잠금을 위해 WAL 레코드를 생성한다는 점이 원인이었습니다. 이 글은 고성능 시스템에서 단순한 쿼리 최적화 가정이 어떻게 물리적 성능 병목으로 이어질 수 있는지, 그리고 이를 어떻게 진단했는지 설명합니다. ### 효율적인 업서트 테이블 설계 * **업데이트 비용 절감:** PostgreSQL은 MVCC(MultiVersion Concurrency Control)를 사용하므로 업데이트 시마다 새로운 행 버전이 생성됩니다. 메타데이터 테이블의 비대화를 막기 위해 `last_ingested` 필드를 별도의 전용 테이블로 분리하여 쓰기 데이터양을 최소화했습니다. * **HOT(Heap-Only Tuples) 업데이트 활용:** 인덱스가 있는 컬럼을 수정하면 인덱스 페이지도 함께 수정되어야 합니다. 이를 피하기 위해 `last_ingested` 컬럼에는 인덱스를 생성하지 않았으며, `fillfactor`를 80%로 설정하여 페이지 내 여유 공간을 확보함으로써 HOT 업데이트가 가능하도록 설계했습니다. * **업데이트 빈도 제한:** 7일간 데이터가 없는 호스트를 식별하는 것이 목적이므로 1일 단위의 정밀도로 충분했습니다. 따라서 `WHERE` 절을 사용하여 마지막 업데이트로부터 24시간이 지난 경우에만 실제 쓰기가 발생하도록 쿼리를 구성했습니다. ### 예상치 못한 성능 지표의 변화 * **I/O 및 WAL 동기화 급증:** 쿼리 배포 후 업데이트 속도는 예상대로 낮게 유지되었으나, 디스크 쓰기 IOPS는 2배, WAL sync 횟수는 4배나 증가했습니다. * **쓰기 예산 소모:** PostgreSQL 클러스터는 단일 라이터(writer) 구조이므로 처리 가능한 쓰기 작업량에 한계가 있습니다. 실제 데이터 변경이 없는 'No-op' 쿼리들이 이 한정된 자원을 과도하게 소모하는 문제가 발생했습니다. * **내부 동작의 모순:** `INSERT ... ON CONFLICT DO UPDATE` 문에서 `WHERE` 조건이 거짓(false)이 되어 행이 업데이트되지 않더라도, 데이터베이스는 동시성 제어를 위해 해당 행에 락(lock)을 겁니다. 이 잠금 행위 자체가 WAL에 기록되면서 물리적인 쓰기 부하를 유발한 것입니다. ### pg_walinspect를 이용한 심층 진단 * **WAL 레코드 조사:** Postgres 15에서 도입된 `pg_walinspect` 확장 프로그램을 사용하여 실제 WAL에 어떤 데이터가 기록되고 있는지 분석했습니다. * **진단 도구 설정:** `pg_get_wal_records_info` 함수를 호출하여 특정 LSN(Log Sequence Number) 범위 내의 레코드를 확인했습니다. 이를 통해 쿼리 실행 시 업데이트가 발생하지 않음에도 불구하고 WAL 레코드가 생성되는 과정을 구체적으로 확인했습니다. * **원인 규명:** 분석 결과, `ON CONFLICT` 상황에서 잠금 처리가 WAL에 기록되는 것을 확인했으며, 이것이 전체적인 디스크 I/O 상승의 주범임을 입증했습니다. ### 실용적인 제언 PostgreSQL에서 고빈도 업서트를 설계할 때는 `WHERE` 조건문이 애플리케이션 레벨의 논리적 업데이트는 막아줄 수 있지만, 데이터베이스 엔진 레벨의 물리적 쓰기(WAL)까지 완전히 차단하지 못할 수 있음을 유의해야 합니다. 극도로 높은 처리량이 요구되는 환경에서는 `pg_walinspect`와 같은 도구를 사용하여 쿼리의 물리적 오버헤드를 사전에 검증하고, 불필요한 잠금 발생을 줄이는 방향으로 쿼리를 재작성하는 과정이 필수적입니다.

datadog

When an AI agent came knocking: Catching malicious contributions in Datadog’s open source repos (새 탭에서 열림)

데이터독(Datadog)은 최근 GitHub Actions 및 LLM 기반 워크플로우를 표적으로 삼는 AI 에이전트 'hackerbot-claw'의 악성 기여 시도를 성공적으로 차단했습니다. 이 공격은 AI 기술을 활용해 오픈소스 리포지토리에 취약점을 주입하려는 시도였으나, 데이터독의 AI 기반 탐지 시스템인 'BewAIre'와 선제적인 CI/CD 보안 제어 덕분에 무력화되었습니다. 이번 사례는 공격자들이 LLM을 통해 공격 규모를 확장함에 따라, 방어자 또한 AI를 보안 체계에 적극적으로 도입해야 함을 시사합니다. **오픈소스 CI 파이프라인을 향한 주요 공격 벡터** - **변수 삽입 취약점:** PR 제목과 같이 사용자가 제어할 수 있는 변수를 워크플로우 스크립트 내에 안전하지 않게 삽입하는 경우를 악용합니다. - **I-PPE(간접 포이즌 파이프라인 실행):** 악성 의존성이나 빌드 지침을 PR에 삽입하여 빌드 과정에서 자동으로 실행되게 함으로써 CI 비밀번호(Secrets)를 탈취합니다. - **`pull_request_target` 오용:** 신뢰할 수 없는 PR에서 실행되는 워크플로우에 높은 권한을 부여하는 설정을 악용하여 시스템을 장악합니다. - **LLM 프롬프트 인젝션:** `claude-code-action`이나 `run-gemini-cli`처럼 LLM을 사용하는 GitHub 액션에 악의적인 지시를 주입하여 자동화된 트리징 시스템을 교란합니다. **AI 기반 탐지 시스템 'BewAIre'의 운영** - **실시간 코드 리뷰:** 매주 유입되는 약 10,000건의 내외부 PR을 대상으로 LLM 기반의 자동화된 보안 검사를 수행합니다. - **2단계 분석 파이프라인:** GitHub 이벤트를 통해 코드 차분(diff) 데이터를 추출 및 정규화한 뒤, 2단계 LLM 파이프라인을 거쳐 변경 사항을 '악성' 또는 '정상'으로 분류하고 그 근거를 구조화하여 제시합니다. - **SIEM 통합 및 대응:** 악성으로 판정된 결과는 즉시 Datadog Cloud SIEM으로 전송되어 보안 사고 대응 팀(SIRT)이 즉각적으로 조사하고 사고화할 수 있도록 지원합니다. **선제적인 인프라 강화 및 보안 모범 사례** - **최소 권한의 임시 자격 증명:** OIDC identity federation을 활용한 `dd-octo-sts-action`을 도입하여, 수명이 길고 권한이 과도한 개인 액세스 토큰(PAT) 대신 수명이 짧고 권한이 제한된 인증 정보를 동적으로 생성합니다. - **비밀 정보 관리:** 수천 개의 리포지토리를 전수 조사하여 사용되지 않는 GitHub Actions 비밀 정보를 대규모로 식별하고 제거했습니다. - **CI 보안 정책 강제화:** 브랜치 보호 규칙, 휴먼 및 봇의 커밋 서명 의무화, 필수 PR 승인 절차를 도입하고 `GITHUB_TOKEN` 권한을 기본적으로 최소 수준으로 설정했습니다. - **보안 골든 패스(Golden Paths):** 엔지니어들이 별도의 복잡한 설정 없이도 보안이 확보된 표준 CI 파이프라인을 사용할 수 있도록 가이드를 문서화하고 시스템화했습니다. AI 에이전트를 활용한 공격이 현실화됨에 따라 단순한 규칙 기반의 탐지는 한계에 직면해 있습니다. 조직은 BewAIre와 같은 AI 기반 탐지 모델을 구축함과 동시에, OIDC를 통한 인증 체계 개선 및 GITHUB_TOKEN 권한 최소화와 같은 근본적인 CI/CD 보안 설정을 병행하여 자동화된 공격에 대한 방어 계층을 다각화해야 합니다.

datadog

에이전트를 위한 MCP 도구 설계: Datadog의 MCP 서버 구축을 통해 배운 교훈 (새 탭에서 열림)

AI 에이전트를 위한 관측성(Observability) 인터페이스 구축 시, 단순히 기존 API를 그대로 노출하는 방식은 컨텍스트 창의 한계와 비용 문제로 인해 한계가 명확합니다. Datadog은 MCP(Model Context Protocol) 서버를 구축하며 데이터 포맷 최적화, SQL 기반 쿼리 도입, 도구의 효율적 관리라는 세 가지 핵심 설계를 통해 에이전트의 작업 효율을 극대화했습니다. 결과적으로 이러한 설계 변경은 에이전트의 추론 정확도를 높이는 동시에 토큰 사용량을 줄여 운영 비용을 절감하는 효과를 가져왔습니다. ### 컨텍스트 창 효율성 극대화 * **데이터 포맷 최적화**: JSON은 프로그래밍 방식에는 적합하지만 토큰 소모가 큽니다. 평면적인 데이터에는 CSV(토큰 약 50% 절감)를, 계층 구조가 있는 데이터에는 YAML(약 20% 절감)을 사용하여 동일한 컨텍스트 내에 더 많은 정보를 담았습니다. * **필드 트리밍**: 에이전트에게 불필요한 필드를 기본 출력에서 제거하고 필요한 경우에만 요청하게 함으로써, 동일한 토큰 예산 내에서 레코드 수용량을 최대 5배까지 늘렸습니다. * **토큰 기반 페이지네이션**: 레코드 개수 단위로 데이터를 끊어 보내는 전통적인 방식 대신, 실제 소비되는 토큰량을 기준으로 응답을 제한하여 에이전트의 컨텍스트 창이 예기치 않게 가득 차는 문제를 방지했습니다. ### 단순 조회를 넘어선 SQL 기반 쿼리 도입 * **서버 측 집계**: 에이전트가 수천 개의 로그를 직접 내려받아 트렌드를 분석하는 대신, 서버에서 SQL을 실행하여 요약된 결과만 받도록 개선했습니다. * **비용 및 성능 개선**: SQL을 통해 꼭 필요한 필드만 선택(SELECT)하고 행을 제한(LIMIT)함으로써, 평가 시나리오에서 실행 비용을 약 40% 절감하고 정답률을 높였습니다. * **에이전트 적응력**: AI 에이전트는 SQL 작성에 매우 능숙하며, 이를 통해 컨텍스트 윈도우에 들어갈 데이터를 스스로 세밀하게 제어할 수 있게 되었습니다. ### 도구 비대화 방지 및 관리 전략 * **유연한 도구 설계**: 개별 API 엔드포인트마다 도구를 만드는 대신, 하나의 도구가 여러 유즈케이스를 처리할 수 있도록 스키마를 범용적으로 설계하여 도구의 총 개수를 줄였습니다. * **도구 세트(Toolsets) 분리**: 모든 도구를 한꺼번에 노출하지 않고, 핵심 도구와 특정 워크플로우를 위한 선택적 도구 세트를 구분하여 에이전트의 혼란을 방지하고 컨텍스트 소모를 최소화했습니다. * **도구 계층화**: "어떻게 작업을 수행할지"를 묻는 도구와 실제 동작 도구를 분리하여 검색 효율을 높였습니다. 다만, 이 방식은 레이턴시 증가라는 기회비용이 발생하므로 신중한 적용이 필요합니다. AI 에이전트를 위한 도구를 설계할 때는 인간 사용자를 위한 API 설계와는 다른 접근이 필요합니다. 에이전트가 데이터를 직접 처리하게 두기보다, 서버 측에서 데이터를 가공하고 요약할 수 있는 강력한 쿼리 기능을 제공하고 전송 포맷을 최적화하는 것이 성능과 비용 측면에서 모두 유리합니다.

datadog

How we reduced the size of our Agent Go binaries by up to 77% (새 탭에서 열림)

Datadog은 에이전트 바이너리 크기가 5년 사이 3배 이상 비대해진 문제를 해결하기 위해, 기능 삭제 없이 Go 바이너리 크기를 최대 77% 줄이는 성과를 거두었습니다. 이들은 체계적인 의존성 감사, 코드 리팩토링, 링커 최적화 복원을 통해 1.22 GiB에 달하던 아티팩트를 5년 전 수준으로 되돌렸으며, 이 과정에서 발견한 Go 컴파일러의 특성을 활용해 Kubernetes 등 다른 대규모 오픈소스 프로젝트에도 기여했습니다. ### 데이터독 에이전트의 빌드 구조와 비대화 문제 * 데이터독 에이전트는 단일 제품처럼 보이지만, 실제로는 OS, 아키텍처, 환경(Docker, K8s, IoT 등)에 따라 수십 개의 서로 다른 빌드 구성을 가집니다. * 수백 개의 외부 라이브러리(Cloud SDK, 컨테이너 런타임 등)를 사용하며, Go 빌드 태그와 의존성 주입(Dependency Injection)을 통해 기능을 제어합니다. * 5년간의 기능 추가로 인해 Linux amd64 패키지의 압축 전 크기가 428MiB에서 1,248MiB로 약 192% 증가했으며, 이는 네트워크 비용 상승과 서버리스/IoT 환경에서의 사용 제약을 초래했습니다. ### Go 의존성 제거를 위한 전략적 접근 * **컴파일러의 패키지 처리 이해**: Go 컴파일러는 패키지 단위로 동작하며, 빌드 제약 조건에 맞는 파일 내에서 `main` 패키지로부터 전역적으로 도달 가능한(reachable) 모든 임포트를 포함합니다. * **빌드 태그 활용**: 불필요한 의존성을 포함하는 파일에 특정 빌드 태그(`//go:build`)를 추가하여, 해당 기능이 필요 없는 빌드에서는 컴파일 단계부터 제외되도록 구성했습니다. * **심볼 분리 및 리팩토링**: 무거운 의존성을 사용하는 특정 함수나 심볼을 별도의 패키지로 격리했습니다. 이를 통해 해당 기능이 꼭 필요한 바이너리에서만 해당 패키지를 임포트하도록 구조를 개선했습니다. ### 바이너리 분석 및 시각화 도구 활용 * **`go list`**: 특정 OS와 아키텍처, 빌드 태그 조합에서 포함되는 패키지 목록을 추출하여 의존성 현황을 파악했습니다. * **`goda`**: 패키지 임포트 관계를 그래프로 시각화하여, 특정 무거운 패키지가 어떤 경로를 통해 바이너리에 포함되었는지 추적했습니다. * **`go-size-analyzer`**: 바이너리 내부에서 각 의존성 패키지가 차지하는 실제 바이트 크기를 텍스트나 인터팩티브 웹 화면으로 분석하여 최적화 우선순위를 정했습니다. * **링커의 한계 파악**: 단순 임포트만으로도 `init` 함수 실행이나 전역 변수 초기화가 발생하여 링커가 해당 코드를 제거하지 못하는 경우가 있음을 확인하고 이를 관리했습니다. 대규모 Go 프로젝트에서 바이너리 크기를 줄이려면 단순한 코드 최적화를 넘어, `goda`나 `go-size-analyzer` 같은 도구로 의존성 그래프를 분석하고 빌드 태그를 활용해 패키지 간의 결합도를 낮추는 아키텍처적 접근이 필수적입니다. 특히 사용하지 않는 기능이 `init` 함수나 리플렉션(reflection)으로 인해 링커 최적화를 방해하지 않도록 주의 깊게 설계해야 합니다.

datadog

런타임 보안을 위한 eBPF 강화: Datadog Workload Protection의 교훈 (새 탭에서 열림)

Datadog은 지난 5년간 수천 개의 환경에서 eBPF 기반의 런타임 보안 제품인 'Workload Protection'을 운영하며 얻은 실전 경험과 교훈을 공유합니다. eBPF는 기존 커널 모듈이나 감사(Audit) 프레임워크보다 안전하고 효율적이지만, 대규모 운영 환경에서는 커널 호환성이나 성능 오버헤드 같은 복잡한 문제들이 발생합니다. 결론적으로 eBPF는 강력한 도구이나, 실제 운영 환경에서 신뢰성을 확보하기 위해서는 단순한 구현을 넘어 정교한 모니터링과 배포 전략이 필수적입니다. **기존 커널 모니터링 기술의 한계와 평가** * **커널 모듈(LKM):** 시스템의 거의 모든 부분을 제어할 수 있는 강력한 권한을 가지지만, 코드 오류가 커널 전체의 크래시로 이어질 수 있어 안정성 측면에서 위험부담이 큽니다. * **전통적인 트레이싱 인터페이스:** inotify, fanotify, kprobes 등은 시스템 내부를 들여다볼 수 있게 해주지만, 전체적인 시스템 활동을 파악하려면 여러 도구를 복잡하게 조합해야 하는 파편화 문제가 있습니다. * **ptrace 및 seccomp-bpf:** 사용자 공간의 프로세스를 추적하는 데 유용하지만, 모든 프로세스 액세스를 감시하기에는 성능 오버헤드가 발생하며 커널 수준의 가시성이 부족합니다. * **Linux Audit 프레임워크:** 가장 널리 사용되는 보안 솔루션이지만, 대량의 이벤트가 발생할 때 시스템 성능에 상당한 영향을 미치는 단점이 있습니다. **보안 제품에 eBPF를 선택한 핵심 이유** * **검증된 안전성:** eBPF 프로그램은 로드되기 전 커널 검증기(Verifier)를 통해 무한 루프나 잘못된 메모리 접근 여부를 정적으로 분석하므로 커널 모듈보다 훨씬 안전합니다. * **통합 가시성:** 프로세스 실행, 파일 시스템 접근, 네트워크 활동 등을 단일 메커니즘으로 모두 추적할 수 있어 시스템 전반에 대한 통합적인 가시성을 제공합니다. * **컨테이너 최적화:** 네임스페이스(Namespace)와 cgroup에 대한 이해도가 높아 컨테이너 환경에서 일관된 모니터링이 가능하며, 특히 CO-RE(Compile Once – Run Everywhere) 도입으로 배포가 쉬워졌습니다. * **강력한 제어 권한:** BPF LSM 기능을 통해 단순한 모니터링을 넘어 시스템 호출을 차단하는 등의 강제 접근 제어(Mandatory Access Control)를 수행할 수 있습니다. **대규모 생산 환경에서의 운영 교훈** * **커널 호환성 유지:** 특정 커널 버전에서는 작동하지만 다른 버전에서는 실패하는 경우를 방지하기 위해 프로그램 로드 및 부착(Attach) 과정을 정교하게 관리해야 합니다. * **성능 비용 관리:** eBPF가 효율적이긴 하지만, 수많은 훅(Hook)이 동시에 실행될 때 발생하는 성능 비용을 지속적으로 측정하고 제어하는 메커니즘이 필요합니다. * **풍부한 데이터 처리:** 캡처된 원시 데이터를 단순히 전달하는 것이 아니라, 보안 분석에 유용하도록 문맥(Context)을 보강하고 정확하게 강화하는 로직이 중요합니다. * **안전한 변경 배포:** 수천 대의 호스트에 영향을 줄 수 있으므로, eBPF 프로그램의 변경 사항을 안전하게 롤아웃하고 문제 발생 시 즉시 감지할 수 있는 시스템을 갖춰야 합니다. **실용적인 제언** eBPF를 도입할 때 "안전하고 성능 저하가 없다"는 마케팅적 수사에만 의존해서는 안 됩니다. 모니터링하려는 워크로드의 특성에 따라 성능 임팩트가 달라질 수 있으므로, 자체적인 성능 모니터링 지표를 구축하고 커널 버전별로 철저한 회귀 테스트를 거치는 것을 추천합니다.