Keyv 공급망 공격: 지금 바로 알아야 할 사항
요약
Keyv 및 관련 npm 패키지들이 Shai-Hulud 공급망 공격으로 인해 침해되었습니다. 공격자는 유지 관리자 계정을 탈취하여 환경 변수와 API 키 등 민감한 정보를 탈취하는 악성 코드를 주입했습니다.
핵심 포인트
- Keyv 코어 및 Redis, MongoDB 등 다양한 어댑터 패키지 침해
- 유지 관리자 계정 탈취 및 타이포스쿼팅 공격 방식 사용
- 애플리케이션 기능은 정상 작동하며 민감 정보만 조용히 탈취
- package-lock.json 감사 및 모든 비밀 정보(secrets) 교체 권고
Keyv 공급망 공격: 지금 바로 알아야 할 사항
Meta Description: Keyv 및 관련 패키지들이 활발한 Shai-Hulud 공급망 공격으로 인해 침해되었습니다 — 어떤 일이 발생했는지, 누가 영향을 받았는지, 그리고 프로젝트를 즉시 보호하는 방법을 설명합니다.
TL;DR: Shai-Hulud 공급망 공격으로 인해 Keyv 및 여러 관련 npm 패키지가 침해되었으며, 영향을 받은 Node.js 애플리케이션에서 환경 변수(environment variables)와 비밀 정보(secrets)를 탈취할 수 있는 악성 코드가 주입되었습니다. 만약 Keyv 또는 그 어댑터(adapter) 패키지 중 하나라도 사용 중이라면, 지금 즉시 의존성(dependencies)을 감사해야 합니다. 이 글은 정확히 어떤 일이 일어났는지, 어떤 패키지가 영향을 받았는지, 그리고 오늘 당장 취해야 할 구체적인 단계들을 분석합니다.
핵심 요약 (Key Takeaways)
- 널리 사용되는 Node.js 키-값 저장소 추상화 라이브러리인 Keyv와 여러 관련 패키지들이 Shai-Hulud라고 불리는 조직적인 공급망 공격(supply chain attack)으로 인해 침해되었습니다.
- 캐싱 및 저장소 추상화를 위해 Keyv에 의존하는 개발자들을 겨냥하여 악성 버전들이 npm 레지스트리에 게시되었습니다.
- 공격 벡터는 원본 코드베이스의 결함이 아니라, **타이포스쿼팅(typosquatting) 및 유지 관리자 계정 탈취(maintainer account compromise)**를 포함합니다.
- 영향을 받은 패키지에는 Keyv 코어 및 여러 저장소 어댑터(Redis, MongoDB, SQLite 등)가 포함됩니다.
- 즉각적인 조치 필요:
package-lock.json을 감사하고, 모든 비밀 정보(secrets)를 교체(rotate)하며, 검증된 깨끗한 버전으로 고정(pin)하십시오. - 이번 사건은 왜 **소프트웨어 공급망 보안(software supply chain security)**이 DevSecOps 워크플로우에서 전용 영역을 가져야 하는지를 보여주는 교과서적인 사례입니다.
Shai-Hulud 공급망 공격이란 무엇인가?
Shai-Hulud 공격은 Frank Herbert의 소설 _Dune_에 등장하는 거대한 모래벌레의 이름을 따서 명명되었으며, 이는 공격의 지하 터널링(tunneling) 특성을 암시하는 것으로 보입니다. 이 공격은 npm 생태계를 겨냥한 활발하고 조직적인 캠페인입니다. 보안 연구원들은 2026년 중반, Node.js 생태계에서 가장 많이 다운로드되는 키-값 저장소 라이브러리 중 하나인 Keyv의 게시된 버전에서 이상 징후가 감지되었을 때 이 공격을 처음 보고했습니다.
이 공격의 핵심은 오픈 소스 생태계에서 우려스러울 정도로 흔해진 패턴을 따릅니다. 즉, 유지 관리자 계정(maintainer accounts)을 탈취하여 겉보기에는 합법적으로 보이는 악성 패키지 버전을 배포하는 방식입니다. 주입된 페이로드(payload)는 매우 교묘합니다. 기능에 문제를 일으키지 않는데, 바로 이 점이 공격을 매우 위험하게 만듭니다. 애플리케이션은 정상적으로 작동하는 것처럼 보이지만, 그동안 악성 코드는 환경 변수(environment variables), API 키, 데이터베이스 자격 증명(database credentials) 및 기타 민감한 데이터를 조용히 수집합니다.
[INTERNAL_LINK: npm 공급망 공격 개요]
Keyv가 고가치 타겟이었던 이유
Keyv는 소수의 사용자만 사용하는 유틸리티가 아닙니다. 매주 수천만 건의 다운로드를 기록하며, 방대한 범위의 Node.js 애플리케이션, 프레임워크 및 도구에서 저장소 추상화 계층(storage abstraction layer) 역할을 수행합니다. 많은 개발자가 이를 간접적으로 사용하는데, 즉 의존성의 의존성(dependency of dependencies) 관계에 있습니다. 주요 다운스트림(downstream) 소비자로는 인기 있는 캐싱 미들웨어, 세션 관리 라이브러리, 심지어 몇몇 잘 알려진 API 프레임워크 등이 포함됩니다.
이 라이브러리의 아키텍처, 즉 코어 패키지(core package)와 일련의 저장소 어댑터(storage adapters)로 구성된 구조는 공격자에게 여러 공격 표면(attack surfaces)을 제공했습니다. 단 하나의 어댑터 패키지만 탈취하더라도 생태계의 상당 부분에 영향을 미칠 수 있었습니다.
어떤 패키지들이 침해되었는가?
npm 보안 팀과 독립 연구자들의 공개 자료에 따르면, Shai-Hulud 캠페인의 일환으로 다음과 같은 패키지들에 악성 버전이 게시되었습니다:
| 패키지 | 침해된 버전 | 상태 |
|---|---|---|
keyv | 4.x 범위 내 특정 마이너/패치 버전 | 깨끗한 버전으로 복구됨 |
| ... |
중요: 침해된 릴리스의 정확한 버전 번호는 공식 npm 보안 권고(security advisories) 및 Keyv GitHub 저장소의 보안 공지를 통해 확인해야 합니다. 이 글을 작성하는 시점에도 영향 범위가 완전히 열거되고 있었기 때문입니다. 조치를 취하기 전에 항상 공식 출처와 대조하여 확인하십시오.
악성 페이로드는 실제로 무엇을 하는가?
주입된 코드를 역공학(Reverse-engineering)한 연구원들은 다단계 페이로드(Multi-stage payload)를 발견했습니다:
- 환경 변수 유출 (Environment variable exfiltration): 패키지 초기화 시, 악성 코드는
process.env를 읽고 모든 환경 변수를 직렬화(Serialize)합니다. - 아웃바운드 비콘 (Outbound beacon): 데이터는 인코딩된 후, 텔레메트리(Telemetry) 엔드포인트로 위장하여 공격자가 제어하는 도메인으로 HTTPS POST 요청을 통해 전송됩니다.
- 지속성 시도 (Persistence attempt): 일부 변종의 경우, 코드는 프로젝트의
node_modules/.bin디렉토리에 작은 로더(Loader)를 쓰려고 시도합니다. - 난독화 (Obfuscation): 페이로드는 단순한 정적 분석(Static analysis)을 피하기 위해 base64 인코딩과 문자열 연결(String concatenation)을 사용합니다.
여기서 나타난 정교함은 주목할 만합니다. 이것은 스크립트 키디(Script kiddie) 수준의 작업이 아닙니다. 공격자들은 기본적인 CI/CD 보안 검사를 피하는 방법을 명확히 이해하고 있었습니다.
공격이 발생한 방식: Shai-Hulud 공격 체인
공격 메커니즘을 이해하는 것은 향후 유사한 사건에 방어하는 데 도움이 됩니다.
1단계: 관리자 계정 탈취 (Maintainer Account Compromise)
보안 연구원들은 초기 침투 경로가 Keyv 생태계와 관련된 npm 관리자 계정을 겨냥한 **크리덴셜 스터핑(Credential stuffing) 또는 피싱(Phishing)**이었을 것으로 보고 있습니다. 공격자가 패키지에 대한 게시 권한을 얻게 되면, 해당 패키지를 설치하거나 업데이트하는 모든 프로젝트로 향하는 직접적인 파이프라인을 사실상 확보하게 됩니다.
2단계: 악성 버전 배포 (Malicious Version Publication)
공격자들은 대충 훑어보았을 때는 통과할 수 있는 새로운 패치 또는 마이너 버전을 게시했습니다. 변경 로그(Changelog)는 그럴듯했고, 버전 상승(Version bump)은 미미했습니다. 이는 npm 생태계의 근본적인 신뢰 가정, 즉 '알려진 신뢰할 수 있는 패키지의 새 버전은 안전하다'는 점을 악용합니다.
3단계: 유기적 배포 (Organic Distribution)
Keyv와 그 어댑터(Adapter)들이 매우 널리 사용되기 때문에, 악성 버전은 게시된 지 몇 시간 만에 전 세계의 CI/CD 파이프라인, Docker 빌드 및 개발 환경으로 유입되었습니다. 버전을 고정(Pinned versions)하지 않고 npm install 또는 npm update를 실행한 개발자들은 소리 없이 피해를 입었습니다.
4단계: 데이터 유출 (Data Exfiltration)
해당 패키지가 초기화되는 모든 환경 — Keyv의 캐싱 레이어 (caching layer) 역할을 고려할 때, 이는 주로 애플리케이션 시작 시 발생합니다 — 의 환경 변수(environment variables)가 소리 없이 유출되었을 것입니다.
[INTERNAL_LINK: how to secure npm dependencies]
즉각적인 조치: 지금 바로 해야 할 일
Keyv 또는 그 어댑터 패키지 중 하나라도 사용 중이라면, 다음 단계들을 완료할 때까지 이를 활성 사고(active incident)로 간주하십시오.
1. 즉시 종속성 감사 (Audit Your Dependencies)
현재 사용 중인 버전을 확인하기 위해 다음 명령어를 실행하십시오:
npm list keyv
npm list @keyv/redis
npm list @keyv/mongo
...
출력된 결과를 공식 보안 권고(security advisories)와 대조하십시오. 직접적인 종속성(direct dependencies)뿐만 아니라 간접 종속성(transitive dependencies)도 반드시 확인해야 합니다.
더 광범위한 감사를 위해, Socket Security와 같은 도구는 npm audit이 제공하는 수준을 넘어선 심층적인 공급망 분석(supply chain analysis)을 제공합니다. Socket은 알려진 CVE뿐만 아니라 패키지의 행동 이상(behavioral anomalies)을 능동적으로 모니터링합니다.
2. 모든 비밀 정보(Secrets) 즉시 교체
침해되었다고 가정하십시오. 만약 귀하의 애플리케이션이 영향을 받은 패키지의 어떤 버전이라도 — 아주 잠시라도 — 사용했다면, 환경에 존재했던 모든 비밀 정보는 유출되었을 가능성이 있는 것으로 간주해야 합니다:
- 데이터베이스 자격 증명 (Database credentials) — 즉시 교체
- API 키 (API keys) (제3자 서비스, 결제 프로세서 등) — 모두 재발급
- JWT 비밀값 및 세션 키 (JWT secrets and session keys) — 교체 및 기존 세션 무효화
- 클라우드 제공업체 자격 증명 (Cloud provider credentials) (AWS, GCP, Azure) — 교체 및 무단 액세스 여부 감사
- 웹훅 비밀값 (Webhook secrets) — 재발급
이는 선택 사항이 아닙니다. 비밀 정보를 교체하는 비용은 침해 사고로 발생하는 비용보다 훨씬 저렴합니다.
3. 깨끗하고 검증된 버전으로 고정 (Pin)
어떤 버전이 안전한지 확인했다면 (공식 권고를 통해), package.json에 종속성을 명시적으로 고정하십시오:
{
"dependencies": {
"keyv": "4.5.4",
...
CI/CD 파이프라인에서는 락파일(lockfile)을 강제하기 위해 npm install 대신 npm ci를 사용하십시오.
4. 서브리소스 무결성(Subresource Integrity) / 패키지 검증 활성화
npm provenance를 활성화하고, 가능한 경우 패키지 서명(package signatures)을 확인하는 것을 고려하십시오. npm 레지스트리는 이제 신뢰할 수 있는 CI 시스템을 통해 게시된 패키지에 대한 provenance 증명(provenance attestations)을 지원합니다.
5. 감사 로그(Audit Logs) 검토
클라우드 제공업체의 감사 로그, 애플리케이션 로그 및 네트워크 송신(egress) 로그를 확인하여 다음 사항을 점검하십시오:
- 익숙하지 않은 도메인으로의 비정상적인 아웃바운드 HTTPS 연결
- 환경 변수(environment variable) 접근의 급증
- 알려진 Shai-Hulud C2 도메인으로의 모든 연결 (현재 목록은 위협 인텔리전스 피드(threat intelligence feeds)를 확인하십시오)
공급망 보안을 강화하기 위한 도구들
이번 사건은 경종을 울리는 계기가 되었습니다. 워크플로우에 통합할 가치가 있는 도구들은 다음과 같습니다:
의존성 스캐닝 및 모니터링 (Dependency Scanning & Monitoring)
-
Socket Security — CVE 스캐닝을 넘어 패키지의 악성 동작 패턴을 탐지합니다. 이번 공격 유형과 직접적인 관련이 있습니다. 솔직한 평가: 공급망 공격을 잡아내는 데 탁월하지만, 통합을 위한 노력이 필요하며 무료 티어 이상의 팀은 비용이 발생합니다.
-
Snyk — 우수한 IDE 통합 기능을 갖춘 광범위한 취약점 스캐닝 도구입니다. 솔직한 평가: 알려진 CVE에는 강력하지만, Shai-Hulud와 같은 제로데이(zero-day) 공급망 공격에는 효과가 덜할 수 있으나, 여전히 가치 있는 기본 계층(baseline layer)입니다.
-
Dependabot — 보안 경고 기능이 포함된 GitHub의 내장 자동 의존성 업데이트 도구입니다. 솔직한 평가: 무료이며 활성화하기 쉽지만, 행동 이상(behavioral anomalies)은 잡아내지 못합니다. 이를 한계치(ceiling)가 아닌 최소한의 기준(floor)으로 사용하십시오.
비밀 관리 (Secret Management)
만약 이번 사건으로 인해 귀사의 비밀 관리 관행에 공백이 드러났다면, 다음을 고려하십시오:
- HashiCorp Vault — 엔터프라이즈급 비밀 관리 (Secret Management). 솔직한 평가: 강력하지만 운영 복잡도가 높습니다. 민감한 워크로드를 처리하는 팀에게는 그만한 가치가 있습니다.
- Doppler — 우수한 CI/CD 통합 기능을 갖춘 개발자 친화적인 비밀 관리 (Secret Management). 솔직한 평가: 소규모 팀이 Vault보다 훨씬 쉽게 도입할 수 있습니다.
Lockfile 보안 (Lockfile Security)
- LockfileCheck — 의심스러운 수정 사항을 확인하기 위해 락파일 (Lockfile)을 감사합니다. 솔직한 평가: 틈새 시장(Niche)용이지만, 락파일 포이즈닝 (Lockfile poisoning) 공격을 잡아내는 데 진정으로 유용합니다.
더 큰 그림: 공급망 공격이 가속화되는 이유
Keyv와 그 주변 라이브러리들을 대상으로 한 Shai-Hulud 공격은 고립된 사건이 아닙니다. 이는 이미 잘 확립된 패턴을 따르고 있습니다:
- SolarWinds (2020) — 국가 지원 해커 그룹이 빌드 시스템을 침해
- event-stream (2018) — 인기 있는 npm 패키지에 악성 코드 주입
- ua-parser-js (2021) — 유지 관리자 계정을 탈취하여 멀웨어 배포
- node-ipc (2022) — 유지 관리자가 의도적으로 자신의 패키지를 파괴
- Shai-Hulud / Keyv (2026) — 가치가 높은 생태계를 겨냥한 조직적인 캠페인
트렌드는 명확합니다: **오픈 소스 의존성 (Open-source dependencies)은 주요 공격 표면 (Attack surface)**이며, 경제적 측면에서도 공격자에게 유리합니다. 단 하나의 침해된 패키지가 수백만 개의 애플리케이션에 도달할 수 있습니다.
[INTERNAL_LINK: npm 공급망 공격의 역사]
업계가 해야 할 일
장기적인 해결책은 단순히 "더 주의를 기울이는 것"이 아닙니다. 구조적인 변화가 필요합니다:
- npm 유지 관리자를 위한 필수 MFA (다요소 인증) (npm이 이 부분에서 진전을 보였으나, 강제 적용은 아직 불완전함)
- **패키지 서명 (Package signing) 및 출처 증명 (Provenance attestation)**이 예외가 아닌 기본값이 되는 것
- 악성 코드가 배포되기 전에 포착하기 위한 레지스트리 (Registry) 수준의 행동 분석 (Behavioral analysis)
- 개발자가 전체 의존성 트리 (Dependency tree)를 이해할 수 있도록 돕는 더 나은 툴링 (Tooling)
자주 묻는 질문 (FAQ)
Q: 제 애플리케이션이 실제로 영향을 받았는지 어떻게 알 수 있나요?
A: 공식 권고 사항(advisories)에 나열된 침해된 버전 번호가 package-lock.json에 있는지 확인하세요. 일치하는 항목을 발견하면, 해당 버전으로 애플리케이션이 실행되던 기간 동안 환경 변수(environment variables)가 유출되었다고 가정해야 합니다. 의심스러운 도메인으로의 연결이 있는지 네트워크 송신(egress) 로그를 검토하세요.
Q: 지금 Keyv를 사용해도 안전한가요?
A: 네, 공격 이후에 출시되었고 유지 관리자(maintainers)에 의해 안전함이 확인된 깨끗한 버전을 사용 중인지 확인했다면 안전합니다. Keyv 프로젝트 자체는 합법적이며 활발한 기여자들에 의해 유지 관리되고 있습니다. 이번 공격은 라이브러리 설계의 근본적인 결함이 아니라, 배포 메커니즘(distribution mechanism)을 대상으로 한 공격이었습니다.
Q: npm audit이 이 공격을 잡아낼 수 있나요?
AI 자동 생성 콘텐츠
본 콘텐츠는 Dev.to AI tag의 원문을 AI가 자동으로 요약·번역·분석한 것입니다. 원 저작권은 원저작자에게 있으며, 정확한 내용은 반드시 원문을 확인해 주세요.
원문 바로가기