自動化ツールが「配信経路」に変わった日
ソフトウェアサプライチェーン攻撃が新段階に入った。かつての攻撃は「開発者のマシンに直接侵入してコードを改ざんする」「OSS管理者アカウントを乗っ取ってパッケージを差し替える」といった手法が主流だった。しかし2026年に入り、自動化された依存関係更新ツールそのものが攻撃の配信経路として組織的に悪用されるという、より巧妙な攻撃パターンが浮上している。
ターゲットになったのはRenovateとDependabot——世界中の開発チームが「依存関係の自動更新」を任せてきた2つのツールだ。これらは元来、開発チームの作業負荷を下げ、既知の脆弱性を素早くパッチするために設計された。ところが今、その「信頼」と「自動化」という設計上の特性が、攻撃者に逆用されている。
GitGuardianのセキュリティ研究者 Gaetan Ferry が2026年4月に公開したレポートは、これらのツールが「設計上、アップグレードパイプラインを最新に保つために作られたが、攻撃者の配送メカニズムになった」と指摘し、開発コミュニティに衝撃を与えた。2026年3月のAxiosパッケージ侵害事件では、マルウェアが公開されてからわずか5分後に最初のPRが作成され、最終的に895個以上のパブリックリポジトリに感染が広がった。
この記事では、GitGuardianレポートの事実データに基づき、攻撃の仕組みを技術的に解説したうえで、開発環境を守るための具体的な設定方法を示す。数字は公開調査データからの引用であり、推測による数値は含まない。
RenovateまたはDependabotを利用しているチーム。GitHubに自動マージワークフローを設定しているプロジェクト。npm・PyPI・GitHub Actionsのワークフローファイルに依存した開発環境を持つすべての開発者。
攻撃がどのように広がるか、まず全体像を掴んでほしい。悪意あるパッケージ公開から認証情報流出まで、5ステップが人間の関与なしに完結する:

Axiosサプライチェーン攻撃:5分で895リポジトリが感染した経緯
2026年3月に発生したAxiosパッケージのサプライチェーン攻撃は、依存関係自動更新ツールの脆弱性を世界規模で実証した事件だ。AxiosはほぼすべてのNode.jsプロジェクトが依存する超主要ライブラリであり、その感染力は桁違いだった。
攻撃タイムライン
| 経過時間 | 出来事 |
|---|---|
| T+0分 | 攻撃者がnpmにマルウェアを含むAxiosバージョンをアップロード |
| T+5分 | 最初のリポジトリへの修正PRがボットによって作成される |
| T+40分 | jhipster/generator-jhipster にて悪意あるアップグレードが検出される |
| T+56分 | jhipster に対してマージが実行される |
| T+数時間 | 895個以上のパブリックリポジトリが感染版にアップグレード |
| T+翌日 | npmがマルウェア版を削除、対応バージョンが公開 |
このタイムラインが示す最大の問題は「速度」だ。セキュリティチームや npm 自体が汚染を検知して対応するよりも圧倒的に速く、RenovateとDependabotが感染を広げた。
154件のPR、60%が自動マージ
この攻撃で作成されたPRの内訳はGitGuardianのレポートで公開されている:
- 154件のPRがボットアカウントによって開かれた
- Dependabot: 111件
- Renovate: 30件
- その他ボット・手動: 13件
そして最も衝撃的な数字が、154件中95件(約60%)が「ユーザーインタラクションなしにマージされた」という事実だ。
GitGuardianが追跡した527個のリポジトリをさらに分解すると:
- 313個(59%):自動ツールが直接ブランチにプッシュ(PRすら経由しない)
- 214個(41%):プルリクエスト経由で更新
直接ブランチプッシュ形式では、そもそもレビューのステップ自体が存在しない。PRを通すプロジェクトであっても、自動マージ設定があれば結果は同じだ。
Dependabot・Renovateは「脆弱性を早期に修正してくれる安全なツール」として広く認知されている。この信頼が「Botからのメッセージは疑わなくて良い」という習慣を生み、攻撃者はその心理を正確に突いた。Botのアイデンティティは信頼の根拠にならない。
攻撃者の思考プロセス:なぜ依存関係更新ツールが「完璧なターゲット」なのか
Axios侵害がわずか5分でPR作成・60%のリポジトリ自動マージに至った背景を理解するには、攻撃者の視点から設計された攻撃の合理性を把握する必要がある。「なぜRenovate/Dependabotなのか」という問いへの答えが、防御策の本質を照らし出す。
攻撃者にとってのメリット:スケールと自動化の組み合わせ
従来型の侵入攻撃(標的型フィッシング、サーバー侵入、ゼロデイ悪用)は、1回の攻撃で1つのターゲットにしか侵入できない。技術的難易度も高く、発見された時点で侵入経路が塞がれる。
しかしサプライチェーン攻撃は根本的に異なる構造を持つ:
- スケール: 1パッケージの汚染で、そのパッケージに依存する数万リポジトリすべてが潜在的な標的になる。Axiosは週1億回以上ダウンロードされる——1回の侵害で億単位のインストールが影響を受けうる
- 自動配信: パッケージをアップロードした後は、RenovateとDependabotが世界中の各リポジトリへPRを自動作成する。攻撃者の追加作業はゼロだ
- 持続性: 自動マージが設定されているリポジトリでは、発見・削除される前に何百ものリポジトリへ感染が広がる。Axios侵害では削除までの数時間で895リポジトリに達した
- 信頼の悪用: Renovate/DependabotのBotアカウントは「信頼できる自動化ツール」として認識されており、開発者がPRレビューを省略する傾向がある。攻撃者はこの信頼構造を正確に設計に組み込んでいる
攻撃者の侵入経路:3パターンの思考プロセス
パターン1:既存パッケージの管理者アカウントを侵害する
1. npmで週10万DL以上のパッケージを選定(影響範囲の最大化)
2. メンテナのメールアドレスをGitHub / LinkedInから特定
3. credential stuffing(他サービスの漏洩パスワードで試す)またはフィッシングでnpmアカウントを奪取
4. マルウェア(認証情報窃取スクリプト)を含む新バージョンをパッチ版として公開
例: axios 1.7.2 → 1.7.3(変更点はpostinstallスクリプトのみ)
5. Renovate/Dependabotがすべての依存リポジトリにPRを自動作成
6. 自動マージ設定があるリポジトリは即座に感染、シークレットが外部へ送信される
このパターンが最も多用される理由は、「正規の更新PRとの区別が付かない」点だ。パッチバージョンの更新は通常セキュリティ修正を意味するため、開発者はむしろ早くマージしようとする。
パターン2:廃止・放棄パッケージを乗っ取る
1. npm上で3年以上更新されていないが、依然として週1万DL以上あるパッケージを探す
(npmでは放棄パッケージの所有権移転を実際に許可するケースがある)
2. npmのtransfer ownership機能またはメンテナへの直接連絡で所有権を取得
3. マルウェア版を公開し、以降はパターン1と同じ
このパターンの厄介な点は、攻撃者がパッケージの「正規の新しいメンテナ」として振る舞える点だ。メンテナ変更はセキュリティツールで検知されにくい。
パターン3:GitHub Actionsのアクション管理者を狙う
1. GitHub Marketplaceで使用リポジトリ数が多いアクションを選定
2. アクションの管理者GitHubアカウントを侵害
3. 既存バージョンタグが指すコミットをforce pushで差し替え
4. Renovateが「同一タグの新しいSHA」として自動更新PRを作成
5. SHA固定していた開発者も更新を適用してしまう(trivy-action侵害で実証済み)
このパターンはCI/CDの実行コンテキストを直接侵害するため、パッケージ汚染よりも被害が大きい。GitHub ActionsはCI実行中に全シークレットにアクセスできるため、1回のマージで組織のすべてのAWS・GCP・Stripeキーが流出しうる。
攻撃者が狙うタイミング
攻撃者はランダムに攻撃するわけではない。レスポンスが最も遅くなるタイミングを精密に選ぶ:
| タイミング | 攻撃者にとってのメリット |
|---|---|
| 金曜夜〜月曜朝 | セキュリティチームが不在。自動マージが実行されても発見が遅れる |
| 大型連休前後 | 開発者がバックログ処理に追われ、依存関係更新PRのレビューを省略しやすい |
| 大規模カンファレンス期間(KubeCon等) | コミュニティの注目が別に向いており、パッケージレジストリ監視が手薄になる |
| メジャーリリース前夜 | 開発チームが忙しく、「後で確認」が増える |
攻撃者のターゲット選定:GitHubは設定が丸見え
パッケージを選ぶ際、攻撃者は影響範囲と侵害のしやすさのバランスを計算する。そして重要な事実がある——パブリックリポジトリの renovate.json と .github/dependabot.yml は全公開されており、GitHub検索でautomerge設定を持つリポジトリを事前にリストアップできる。
攻撃者が求める「理想的な標的リポジトリ」の条件:
1. automerge: true(またはGitHub自動マージワークフロー設定済み)
2. minimumReleaseAgeなし(公開直後のパッケージも即時PR作成される)
3. CI/CDでGitHub Secrets(AWS, GCP, Stripeキー等)を使用
4. シークレット検出ツール未導入(GitLeaks等なし)
5. ブランチ保護ルールが緩い(レビュアー承認なしでマージ可)
これら5条件をすべて満たすリポジトリは、マルウェア入りパッケージ公開から数時間以内に認証情報を失う。自分のリポジトリが「攻撃者から見えるターゲットリスト」に載っていないか、チェックしてほしい。
次の候補へ"] C -->|"Yes"| D{"依存リポジトリに
automerge設定あり?"} D -->|"確認不可"| E["標準価値:侵害後に自然拡散"] D -->|"多数確認"| F["高価値ターゲット
優先攻撃対象"] F --> G["金曜夜または連休前に
悪意あるパッチ版を公開"] G --> H["Renovate/Dependabotが
世界中にPRを自動作成"] H --> I["自動マージ実行
シークレット窃取完了"]
RenovateとDependabotが攻撃を加速させる3つの仕組み
攻撃の特徴は「人間の関与なしに完結する速度」だ。GlassWorm(不可視Unicode文字を使ったサプライチェーン攻撃)が人間のコードレビューを欺く手法だったのに対し、Renovate/Dependabot経由の攻撃は人間のレビューステップそのものを迂回する。その根拠となる設計原則を3つに整理する。
仕組み1:公開から即座のPR作成
RenovateとDependabotは、パッケージレジストリを定期的にポーリングして新しいバージョンを検知する。新バージョンが公開されると——悪意あるものであっても——即座にPRを作成する設計になっている。
攻撃者の観点から見れば、npmやPyPIに悪意あるパッケージをアップロードするだけで、世界中の数千のリポジトリへの配信経路が自動的に確立される。人間が何もしなくても、ツールが代わりに動いてくれる。このスケーラビリティは攻撃者にとって極めて魅力的だ。
Renovateの設定によっては、パッケージ更新の検知頻度を下げることができるが、デフォルト設定では数時間以内に新バージョンが検知される。
仕組み2:自動マージ設定の普及
GitHubでは、Dependabotのマイナー・パッチ更新を自動でマージするワークフローが広く使われている。GitHub公式ドキュメントにも自動マージのサンプルが掲載されており、多くのプロジェクトがそのまま採用してきた:
# ❌ 危険パターン:Dependabot PRをすべて自動マージするワークフロー
name: Dependabot auto-merge
on: pull_request
permissions:
contents: write
pull-requests: write
jobs:
dependabot:
runs-on: ubuntu-latest
if: $
steps:
- name: Fetch Dependabot metadata
id: metadata
uses: dependabot/fetch-metadata@v2
- name: Enable auto-merge for patch updates
if: $
run: gh pr merge --auto --merge "$PR_URL"
env:
PR_URL: $
GH_TOKEN: $
このワークフローは「パッチ更新は安全だろう」という前提で設計されている。しかしマルウェアは正規のパッチ更新として配信される——1.7.2 から 1.7.3 という形で。パッチ更新だからといって安全ではない。
仕組み3:GitHub Actionsワークフロー更新への適用拡大
RenovateはnpmやPyPIのパッケージだけでなく、GitHub Actionsのワークフローファイル(.github/workflows/*.yml)内のバージョン参照も更新する。
これが第3の攻撃ベクタになる。CI/CDパイプライン自体を更新することで、secretsコンテキスト(全GitHubシークレット)へのアクセス権を持つ悪意あるアクションが実行される。パッケージの侵害よりも被害が大きくなりうる。
RenovateとDependabotの深掘り比較:セキュリティ視点の選定指針
攻撃の仕組みを理解したうえで、「どちらのツールをどう設定するか」という選定判断に移る。「RenovateとDependabotはどちらを使えばいいのか」——チームの規模・GitHub依存度・セキュリティ要件によって答えは変わる。両者の違いを正確に把握することが、設定最適化の前提だ。
アーキテクチャの根本的な違い
| 観点 | Renovate | Dependabot |
|---|---|---|
| ホスト形式 | OSS(セルフホスト可)/ Mend.io提供のSaaS | GitHub組み込み(GitHubのみ) |
| 対応プラットフォーム | GitHub, GitLab, Bitbucket, Azure DevOps等 | GitHubのみ |
| 設定ファイル | renovate.json(高度なJSON/JS設定) |
.github/dependabot.yml(シンプルなYAML) |
| 対応エコシステム数 | 90以上(Helm, Terraform, Docker含む) | 25前後(主流パッケージマネージャー) |
| セットアップ難易度 | 中〜高(設定の学習コスト) | 低(数行のYAMLで動作) |
| GitHub Security Advisory連携 | なし(外部ツール連携が必要) | ネイティブ連携 |
Renovateが「制御の細かさ」で優れている点
Renovateの最大の強みは設定の柔軟性だ。packageRules による条件分岐で、パッケージごと・エコシステムごと・更新タイプごとに異なる振る舞いを指定できる。セキュリティポリシーを細粒度でエンコードできる点が、Dependabotとの最大の差だ。
グルーピング(groupName)——関連パッケージをまとめて1つのPRにする:
// renovate.json: ESLint関連をまとめ、devDepsパッチは一括自動マージ
{
"packageRules": [
{
"matchPackagePatterns": ["^eslint"],
"groupName": "eslint packages",
"automerge": true,
"minimumReleaseAge": "3 days"
},
{
"matchDepTypes": ["devDependencies"],
"matchUpdateTypes": ["patch"],
"groupName": "devDependency patches",
"automerge": true,
"minimumReleaseAge": "3 days"
}
]
}
DependabotにもGroupsオプションはあるが、条件の多重化(depType + updateType + パッケージ名パターンの組み合わせ)はRenovateほど柔軟ではない。PR数を減らしながらもパッケージ単位のリスク管理を維持したい場合、Renovateが有利だ。
スケジューリングの精密な制御——曜日・時間帯を絞る:
// renovate.json: 水曜の業務時間のみPR作成、週末は停止
{
"schedule": ["after 9am and before 5pm on wednesday"],
"timezone": "Asia/Tokyo",
"packageRules": [
{
"matchManagers": ["github-actions"],
"schedule": ["after 9am and before 5pm on tuesday and thursday"]
}
]
}
セキュリティの観点からスケジューリングが重要なのは、「業務時間外の自動マージを防ぐ」ためだ。攻撃者は金曜夜に悪意あるパッケージを公開し、週末中に自動マージが進むのを待つ。業務時間内に限定すればこのパターンを遮断できる。Dependabotはdayとtimeの指定が可能だが、複数曜日・時間帯のAND条件はサポートしていない。
automergeのホワイトリスト制御——信頼済みパッケージのみに絞る:
// renovate.json: 特定の信頼済みパッケージのみ自動マージを許可
{
"packageRules": [
{
"matchPackageNames": ["typescript", "prettier", "@types/node"],
"automerge": true,
"automergeType": "pr",
"automergeStrategy": "squash",
"minimumReleaseAge": "5 days",
"matchUpdateTypes": ["patch", "minor"]
},
{
"matchPackageNames": ["*"],
"automerge": false
}
]
}
「特定パッケージのみ自動マージ許可」というホワイトリスト設計はRenovateの強みだ。Dependabotの自動マージはGitHub Actionsワークフロー側で制御するため、同等のパッケージ単位の細かさを実現するにはワークフローの記述量が大幅に増える。
DependabotがGitHub統合で優れている点
DependabotはGitHubの機能として設計されており、GitHubのセキュリティインフラとのネイティブ統合という点で際立っている。
GitHub Security Advisories DBとの直接連携:
DependabotはGitHub Advisory Databaseと直接統合されており、CVEが登録された瞬間にセキュリティアップデートPRを自動作成する。これは「定期スキャン」ではなく、アドバイザリ登録イベント駆動で動作する点が重要だ。
# .github/dependabot.yml: セキュリティアップデートは有効、通常バージョン更新は制限
version: 2
updates:
- package-ecosystem: "npm"
directory: "/"
schedule:
interval: "weekly"
open-pull-requests-limit: 5
cooldown:
default-days: 3
# Dependabot Alertsによるセキュリティ更新は別途自動発火する
# RenovateではこのCVE連動機能は利用不可(外部ツール連携が必要)
Dependabot Alertsはリポジトリ設定から無料で有効化でき、追加設定なしにCVE通知が届く。Renovateは同等のセキュリティアラート機能を持たず、脆弱性検知はSnyk・Trivy等の外部ツールに委ねる設計だ。
設定の簡潔さ——最短3分で冷却期間付き運用を開始できる:
# .github/dependabot.yml: 必要最低限の安全な設定(5行)
version: 2
updates:
- package-ecosystem: "npm"
directory: "/"
schedule:
interval: "weekly"
cooldown:
default-days: 3
この設定で「週次更新 + 3日冷却期間」が実現する。Renovateで同等の設定を書くには、初期設定(extends、schemaの指定等)のオーバーヘッドがある。セットアップの速さが求められる場面ではDependabotが有利だ。
GitHub Enterprise Serverでの公式サポート:
DependabotはGitHub Enterprise Server(GHES)で公式サポートされており、インターネット非接続環境でも動作する。オンプレミスのGitHub環境を使う組織ではDependabotが唯一の現実的な選択肢になるケースもある。
セキュリティ観点での機能比較
| セキュリティ機能 | Renovate | Dependabot |
|---|---|---|
| 冷却期間の設定精度 | 高(パッケージ単位・エコシステム単位で個別指定可) | 中(エコシステム単位) |
| automerge制御の精度 | 高(packageRules + 多重条件のホワイトリスト) | 中(ワークフロー制御が必要) |
| GitHub Advisory DB連携 | なし(外部ツール連携が必要) | ネイティブ(無料・設定不要) |
| セルフホスト可否 | 可(ネットワーク分離環境でも動作) | 不可 |
| pinDigests(SHA固定) | pinDigests: true で設定可 |
insecure-external-code-execution: deny |
| スケジューリング精度 | 高(曜日・時間帯のAND条件) | 低(曜日・時刻のみ) |
| 設定のバージョン管理 | JSON/JSファイルとしてPRでレビュー可 | YAMLファイル・単一設定 |
| 対応エコシステム | 90以上(Helm, Terraform, Docker含む) | 25前後 |
プロジェクト別の選定指針
Renovateを選ぶべきプロジェクト:
- 大規模モノレポ・多言語プロジェクト: 90以上のエコシステム対応と詳細なpackageRulesで、複雑な依存関係を細かく管理できる
- セキュリティポリシーを厳密にコントロールしたい組織: セルフホストによりパッケージ更新の全フローをコントロールでき、ネットワーク分離環境でも動作する
- PR数の削減とセキュリティを両立したいチーム: groupNameによるグルーピングで関連パッケージをまとめつつ、automergeのホワイトリスト制御でリスクを下げられる
- GitHub以外のプラットフォームも使用: GitLab・Bitbucket・Azure DevOpsでも同じ設定ファイルが使える
Dependabotを選ぶべきプロジェクト:
- GitHub Actionsを中心としたCI/CD: GitHubのセキュリティインフラとのネイティブ統合が最大限に活きる
- 小〜中規模チーム・スタートアップ: 設定が最小限で、追加の学習コストなしにセキュリティアップデートが届く
- GitHub Enterprise Server環境: GHES公式サポートにより、インターネット非接続環境でも動作
- CVE通知を自動受け取りたい: Advisory Database連携による自動セキュリティPRが、Renovateでは実現できないメリットだ
大規模プロジェクトでは「Renovateでパッケージのバージョンアップデートを管理し、DependabotのSecurity Updatesのみ有効にする」という併用構成も有効だ。
dependabot.ymlでバージョン更新を無効化してセキュリティアラートのみ受け取れば、RenovateとDependabotを競合なく共存させられる。CVE通知の即時性とRenovateの細粒度制御を両方得られる。
コミットSHAの固定を破るRenovate:trivy-action事件の教訓
GitHub Actionsのセキュリティベストプラクティスとして長く推奨されてきたのが「コミットSHAによるバージョン固定」だ:
# SHA固定の例(従来は安全とされていた)
steps:
- name: Run Trivy vulnerability scanner
uses: aquasecurity/trivy-action@48d6c1bc7a30e4b4cd7d2cba23f74e21c4e68d75
# ↑ タグではなくコミットSHAで参照
with:
image-ref: 'myapp:latest'
format: 'sarif'
タグ(@v0.20.0 など)は攻撃者が書き換えられるが、コミットSHAは不変——という前提でこの設定が推奨されてきた。しかし2026年3月のtrivy-action侵害は、この前提を崩した。
攻撃の手順はこうだ:
- 攻撃者が
aquasecurity/trivy-actionのメンテナアカウントを侵害する - 既存のバージョンタグが指すコミットを差し替える(force push + タグの移動)
- Renovateが「同一バージョンタグの新しいSHA」として自動更新PRを作成する
- SHA固定だから安全と思っていた開発者がレビューせずにマージ → 感染
SHA固定という保護機構が、Renovateのワークフロー更新機能によって完全に無効化された。
SHA固定は依然として有効な防御策だが、「更新しない」ことを意味しない。更新する際には冷却期間が必要だ:
// renovate.json: GitHub Actionsのワークフロー更新に冷却期間を設定
{
"$schema": "https://docs.renovatebot.com/renovate-schema.json",
"extends": ["config:base"],
"packageRules": [
{
"matchManagers": ["github-actions"],
"pinDigests": true,
"minimumReleaseAge": "5 days",
"description": "GitHub Actions: SHA固定 + 5日間の冷却期間"
}
]
}
この設定により、「タグが書き換えられてもコミュニティが5日以内に発見する時間的余裕」が確保される。実際、trivy-actionの侵害はセキュリティ研究者によって数時間以内に発見・報告されていた。冷却期間があれば、多くのリポジトリが影響を受ける前に対処できた可能性がある。
AIコーディングエージェントが攻撃のリスクを増幅させる
LiteLLMのサプライチェーン侵害では、従来のRenovate/Dependabotによる感染だけでなく、AIコーディングエージェントが攻撃の新たなトリガーになるという前例のないリスクが実証された。
GitGuardianのレポートによると:
AIコーディングエージェントがuvプロジェクトのロックファイルを更新する決定を下し、このAI駆動の意思決定がマルウェアのダウンロードと実行をトリガーした。
これが意味することは深刻だ。開発者がAIエージェント(GitHub Copilot、Claude Code、Cursor等)に「依存関係を最新化して」と指示すると、エージェントは自律的に uv lock や pip install --upgrade や npm update を実行する。この瞬間に悪意あるパッケージが環境に取り込まれ、インストールスクリプトが実行される。
AIエージェントは実行結果を「成功」として報告する。エラーも警告もない。開発者は感染に気づかない。
AIエージェントへの安全な指示の出し方
<!-- CLAUDE.md / .github/copilot-instructions.md への追記例 -->
## 依存関係更新のスコープ制限
AIエージェントは以下の操作を自律的に実行しない:
- npm install / npm update(新パッケージの追加・更新)
- pip install / uv lock(Pythonパッケージの更新)
- go get(Goモジュールの追加・更新)
依存関係の更新が必要な場合は、更新PRのドラフトのみを作成し、
人間のレビュー後に実行すること。
AIエージェントへの「依存関係を更新して」という指示は、人間が手動でバージョンを確認する機会を完全に排除する。エージェントはエラーなく完了するため、開発者は感染に気づかない。
AIエージェントのコンテキストファイル(CLAUDE.md等)で「依存関係の更新は除外する」か「更新PRの作成のみ(実行しない)」と明示的に制限すること。
冷却期間(Cool-off)の設定:公開直後の「汚染ウィンドウ」を避ける
冷却期間(minimumReleaseAge)は、攻撃者の「汚染ウィンドウ」を回避する最も効果的な防御策だ。
悪意あるパッケージが公開されてから、セキュリティコミュニティが検知・パッケージレジストリが削除するまでには通常数時間〜数日かかる。この期間内に自動更新が実行されると感染する。3〜5日の冷却期間を設けることで、「パッケージレジストリが汚染を削除する前に更新しない」という安全マージンが確保できる。
Axios侵害事件を見ても、マルウェアが削除されるまでの時間内に60%のリポジトリが感染した。冷却期間があれば、この60%の大半が感染を免れた可能性がある。
Renovateの冷却期間設定
// renovate.json
{
"$schema": "https://docs.renovatebot.com/renovate-schema.json",
"extends": ["config:base"],
"minimumReleaseAge": "3 days",
"packageRules": [
{
"matchUpdateTypes": ["patch"],
"minimumReleaseAge": "3 days"
},
{
"matchUpdateTypes": ["minor"],
"minimumReleaseAge": "5 days"
},
{
"matchManagers": ["github-actions"],
"minimumReleaseAge": "5 days",
"pinDigests": true
},
{
"matchUpdateTypes": ["major"],
"minimumReleaseAge": "7 days",
"automerge": false
}
]
}
Dependabotの冷却期間設定
# .github/dependabot.yml
version: 2
updates:
- package-ecosystem: "npm"
directory: "/"
schedule:
interval: "weekly"
day: "monday"
cooldown:
default-days: 3
semver-patch-days: 3
semver-minor-days: 5
semver-major-days: 7
ignore:
- dependency-name: "*"
update-types: ["version-update:semver-major"]
- package-ecosystem: "github-actions"
directory: "/"
schedule:
interval: "weekly"
cooldown:
default-days: 5
npmとuvのパッケージマネージャーレベル設定
パッケージマネージャー自体にも冷却期間に相当する設定を追加できる:
# .npmrc(プロジェクトルートまたはホームディレクトリ)
min-release-age=3
audit=true
audit-level=moderate
# pyproject.toml(uvを使用するPythonプロジェクト)
[tool.uv]
exclude-newer = "3 days"
# 公開から3日以内のパッケージをインストール対象から除外
・パッチ更新(x.x.X): 3日間
・マイナー更新(x.X.0): 5日間
・GitHub Actionsワークフロー: 5日間
・メジャー更新(X.0.0): 7日間(自動マージ禁止、手動レビュー必須)
冷却期間の盲点:ゼロデイ対応が遅れるトレードオフ
冷却期間は強力な防御策だが、万能ではない。正直に言えば、重大な脆弱性(CVSS 9.0以上のゼロデイ等)のパッチが公開されたとき、3〜5日の冷却期間は「わかっている脆弱性を意図的に放置する期間」になりうる。
冷却期間は「公開直後のマルウェア」を防ぐが、「公開直後のセキュリティパッチ」も同じく遅らせる。新機能を含むバージョン更新と緊急セキュリティ修正を同じルールで扱うと、防御と対応速度の両方を犠牲にする可能性がある。このトレードオフを認識したうえで設定を組むことが重要だ。
現実的な対処は、バージョン更新(新機能)と脆弱性修正を別ルールで管理する2トラック設計だ:
// renovate.json: 通常更新に冷却期間、脆弱性修正は即時PRで人間レビュー
{
"$schema": "https://docs.renovatebot.com/renovate-schema.json",
"extends": ["config:base"],
"minimumReleaseAge": "3 days",
"vulnerabilityAlerts": {
"enabled": true,
"minimumReleaseAge": null,
"automerge": false,
"labels": ["security", "urgent"],
"addLabels": ["vulnerability-fix"]
},
"osvVulnerabilityAlerts": true
}
# .github/dependabot.yml: バージョン更新に冷却期間、セキュリティ更新は別扱い
version: 2
updates:
# バージョン更新(通常): 冷却期間あり
- package-ecosystem: "npm"
directory: "/"
schedule:
interval: "weekly"
cooldown:
default-days: 3
semver-patch-days: 3
semver-minor-days: 5
# セキュリティアップデートはDependabot Security Updatesが自動発火
# (cooldown設定の対象外、Advisory Database登録と同時にPR作成)
# → Settings > Code security > Dependabot security updates: 有効
この2トラック設計では:
- バージョン更新PRは冷却期間で保護(マルウェア入り新バージョンの即時適用を防ぐ)
- 脆弱性修正PRは冷却期間なしで即時作成・手動レビューで適用(既知CVEへの対応を遅らせない)
「冷却期間を設けているから安全」という過信は危険だ。冷却期間はサプライチェーン攻撃への有効な対策であり、同時にゼロデイ対応の速度を下げるコストを持つ。このトレードオフを理解したうえで設定することが、形式的なセキュリティ対策を超えた本質的な防御につながる。
自動マージ設定の見直し:安全な運用パターン
冷却期間と並んで重要なのが、自動マージ設定の無効化または大幅な制限だ。
自動マージの判断フロー
どの更新を自動マージして良いかを判断するための基準を整理する:
(SHA固定でも例外なし)"] B -->|"No"| D{"冷却期間\n3日以上経過?"} D -->|"No"| E["PRを保留
冷却期間後に再検討"] D -->|"Yes"| F{"メジャー更新?"} F -->|"Yes"| C F -->|"No"| G{"本番シークレットに\nアクセスするパッケージ?"} G -->|"Yes"| C G -->|"No"| H["自動マージ検討可
(CIが全て通過後)"]
危険な自動マージ設定(削除すること)
# ❌ 削除すべき設定:Dependabot PRをすべて自動マージ
name: Dependabot auto-merge (DANGEROUS)
on: pull_request
jobs:
auto-merge:
runs-on: ubuntu-latest
if: $
steps:
- run: gh pr merge --auto --merge "$PR_URL"
env:
GH_TOKEN: $
# ↑ パッチ更新に限定していても危険。マルウェアはパッチ版として配信される
安全な自動マージ設定(推奨構成)
完全な自動マージを禁止したうえで、最小限の条件を課す:
# ✅ 推奨:冷却期間 + CI全通過後のみ自動マージ
name: Dependabot conditional auto-merge
on: pull_request
jobs:
check-and-merge:
runs-on: ubuntu-latest
if: $
steps:
- name: Fetch metadata
id: meta
uses: dependabot/fetch-metadata@v2
with:
github-token: "$"
- name: Block GitHub Actions updates from auto-merge
if: $
run: |
echo "GitHub Actions updates require manual review"
exit 1
- name: Block major updates
if: $
run: |
echo "Major updates require manual review"
exit 1
# パッチ・マイナー更新のみ、CI全通過後に自動マージ
- name: Conditional auto-merge
if: |
steps.meta.outputs.update-type == 'version-update:semver-patch' ||
steps.meta.outputs.update-type == 'version-update:semver-minor'
run: gh pr merge --auto --squash "$PR_URL"
env:
PR_URL: $
GH_TOKEN: $
すべてのPRを人間がレビューするのが理想だが、大規模プロジェクトでは非現実的なこともある。推奨する妥協点:
① GitHub Actionsの更新は例外なく手動レビュー
② パッケージのパッチ・マイナー更新は冷却期間3日後に自動マージ可(CI必須)
③ 本番のシークレット・credentialsにアクセスするパッケージは手動のみ
サプライチェーン攻撃への多層防御:設定チェックリスト
個別の設定変更だけでなく、組織全体での多層防御が重要だ。以下のチェックリストで現在の設定を確認してほしい。
レイヤー1:即座に対応すべき設定変更
| 対策 | Renovate | Dependabot | 優先度 |
|---|---|---|---|
| 冷却期間(3日以上) | minimumReleaseAge: "3 days" |
cooldown.default-days: 3 |
🔴 最高 |
| GitHub Actions更新に冷却5日 | packageRulesでgithub-actionsに適用 | cooldown.default-days: 5(ecosystemで分離) |
🔴 最高 |
| 全自動マージ無効化 | "automerge": false |
ワークフローから自動マージstepを削除 | 🔴 最高 |
| SHA固定(GitHub Actions) | pinDigests: true |
insecure-external-code-execution: deny |
🟠 高 |
| 週次スケジュール | "schedule": ["on monday"] |
interval: "weekly" |
🟡 中 |
レイヤー2:GitHubリポジトリのブランチ保護
# Settings → Branches → Branch protection rules の推奨設定
required_status_checks:
strict: true
contexts:
- "ci / test"
- "security / scan"
require_pull_request_reviews:
required_approving_review_count: 1
dismiss_stale_reviews: true
require_code_owner_reviews: true
restrictions: null # 特定チームに制限する場合は設定
レイヤー3:シークレット検出とモニタリング
最近のサプライチェーン攻撃はシークレット盗難に重点を置いている。 ハニートークン(偽造認証情報)の配置が有効な早期検知手段として注目されている。
ハニートークンとは、実際には使用しない「偽のAPIキー」や「偽のAWSクレデンシャル」を環境変数・設定ファイルに埋め込む手法だ。マルウェアがこれらを盗んで使おうとした瞬間にアラートが発火する:
# CanaryTokens (canarytokens.org) などで生成したハニートークン例
# 実際のシークレットの隣に配置。アクセスされると即座に通知が届く
export CANARY_AWS_ACCESS_KEY="AKIAIOSFODNN7CANARY1"
export CANARY_STRIPE_KEY="sk_live_canary_xxxxxxxxxxxxxxxxxxxxxxxxx"
# 上記はダミー。本物のCanaryTokenサービスで発行したものを使う
また、CI/CDパイプラインにシークレット検出ツールを組み込む:
# .github/workflows/security.yml
name: Security Scan
on: [push, pull_request]
jobs:
secret-scan:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v4
with:
fetch-depth: 0
- name: GitLeaks Secret Scan
uses: gitleaks/gitleaks-action@v2
env:
GITHUB_TOKEN: $
GITLEAKS_LICENSE: $
レイヤー4:定期監査
# どのリポジトリが自動マージ設定を持つか定期的に確認
gh api /repos/{owner}/{repo}/actions/workflows \
--jq '.workflows[] | select(.name | contains("auto-merge")) | .name, .html_url'
# Renovate設定の自動マージ状態を確認
cat renovate.json | jq '.automerge, .packageRules[].automerge'
レイヤー5:SCAツールと代替策による多層補完
冷却期間と自動マージ制御は「新しいマルウェアのインストールを遅らせる」防御だ。しかし冷却期間だけに頼ることは、ほかの攻撃経路を見落とすリスクがある。以下の補完策を組み合わせることで、防御の厚みが増す。
OSV(Open Source Vulnerabilities)データベースとの統合:
RenovateはOSVデータベースと直接統合して脆弱性アラートを受け取れる。GitHub Advisory Databaseより広いカバレッジ(Go, Rust, Python等)を持つため、Dependabotが検知しない脆弱性を補完できる:
// renovate.json: OSV脆弱性アラートを有効化
{
"extends": ["config:base"],
"osvVulnerabilityAlerts": true,
"vulnerabilityAlerts": {
"enabled": true,
"automerge": false,
"labels": ["security"]
}
}
Socket.devによるパッケージ評判スキャン:
Socket.devはnpm・PyPIパッケージの「供給元の評判・挙動分析」に特化したSCAツールだ。Renovate/Dependabotが「新しいバージョンが出た」という事実だけを報告するのに対し、Socket.devは「そのパッケージが怪しい挙動をしていないか」を評判スコアで評価する。
# .github/workflows/socket-security.yml
name: Socket Security Check
on: [pull_request]
jobs:
socket:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v4
- name: Socket Security GitHub Action
uses: SocketDev/socket-security-action@v1
with:
api-key: $
PRにRenovate/DependabotがパッケージアップデートPRを作ると、Socketが同時に実行されてリスクスコアを付ける。リスクが高ければCIが失敗し、自動マージがブロックされる。
GitHub Advanced Security(Dependency Review Action):
GitHub Advanced SecurityのDependency Review Actionは、PRがマージされる前に依存関係の変更を評価し、既知の脆弱性が含まれているかをチェックする:
# .github/workflows/dependency-review.yml
name: Dependency Review
on: [pull_request]
permissions:
contents: read
pull-requests: write
jobs:
dependency-review:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v4
- name: Dependency Review
uses: actions/dependency-review-action@v4
with:
fail-on-severity: moderate
deny-licenses: GPL-2.0, AGPL-3.0
comment-summary-in-pr: always
SLSAプロビナンス検証:
SLSA(Supply chain Levels for Software Artifacts)フレームワークに対応したパッケージは、ビルドの来歴(どのソースコードから、どのビルド環境で作られたか)を検証できる。npm ecosystemでは徐々に対応が進んでいる:
# npm provenance の確認(SLSA Level 2以上のパッケージ)
npm audit signatures
# 署名が正しいパッケージ: "verified"
# 署名なしのパッケージ: "missing"
現時点ではSLSA対応パッケージはまだ少ないが、インストール時に署名検証を有効にしておくことで、将来的な保護が自動的に強化される。
| ツール・手法 | 何を防ぐか | 冷却期間との関係 |
|---|---|---|
| 冷却期間(minimumReleaseAge) | 公開直後のマルウェア入りパッケージ | 基本防御 |
| Socket.dev | 悪意ある挙動・評判スコアが低いパッケージ | 冷却期間を補完(行動ベース) |
| OSV統合 | 既知CVEのある依存関係 | 冷却期間と独立(別経路の検知) |
| Dependency Review Action | PRに含まれるCVE・ライセンス問題 | 冷却期間の後段でさらにチェック |
| SLSA provenance | ビルド来歴が改ざんされたパッケージ | 冷却期間では検知できない攻撃を補完 |
アップグレードパイプラインを「信頼しない」前提で再設計する
GitGuardianのレポートが示す結論は明快だ:
「アップグレードパイプラインは、設計により現在のソフトウェアを保つために作られたが、攻撃者の配送メカニズムになった。セキュリティチームは、自動化層自体に検出フォーカスをシフトすべきだ。」
これは「RenovateやDependabotを使うな」という意味ではない。依存関係の自動更新は現代のソフトウェア開発に不可欠だ。既知の脆弱性を素早く修正するために、これらのツールはむしろ積極的に使うべきだ。
問題は「自動化への盲目的な信頼」にある。
「Botからの更新は安全だろう」という前提を捨て、「どんな経路からの更新でも悪意ある可能性がある」という設計に切り替えることが、2026年以降のサプライチェーンセキュリティの基本姿勢だ。
具体的な行動計画をまとめる:
- 今日中に:
renovate.jsonと.github/dependabot.ymlに冷却期間3日を設定 - 今日中に:自動マージワークフローを削除、または GitHub Actions更新を除外
- 今週中に:
pinDigests: trueでGitHub ActionsのSHA固定を徹底 - 今月中に:ハニートークンを主要リポジトリに配置、シークレットスキャンをCIに追加
- 今月中に:Socket.devまたはDependency Review Actionをパイプラインに統合
- 定期的に:自動マージ設定を持つリポジトリの定期監査スクリプトを実行
GitHub Actions全体のセキュリティ強化については、OIDC認証・最小権限トークン・SLSA対応を含む包括的なガイドも参照してほしい。
完全防御は存在しない——ツールは「補助」、最終ゲートキーパーは人間だ
ここまで紹介してきた設定——冷却期間、automergeのホワイトリスト化、SHA固定、SCAツール統合、ハニートークン——は、いずれも攻撃の確率と影響範囲を下げるための「確率的な防御」だ。「この設定をすれば完全に安全」という組み合わせは存在しない。
この現実を直視することが、過信という最大のリスクを回避する第一歩だ。
冷却期間を設定しても、攻撃者がその期間内に気づかれないパッケージを仕込む可能性はある。SCAツールが評判スコアを「安全」と誤判定するケースもある。SHA固定も、メンテナアカウントが侵害されれば無効化される。
すべての自動化ツールはリスクを「下げる」ものであり「なくす」ものではない。最終防衛線は依然として人間のレビューだ。
人間レビューが最終防衛線であることは、「すべてのPRを人間がレビューしろ」という意味ではない。現実的なアプローチはこうだ:
高リスクカテゴリには例外なく人間のレビューを通す:
- GitHub Actionsのワークフロー更新(CIに直接影響するため)
- 本番のシークレット・クレデンシャルにアクセスするパッケージ
- メジャーバージョン更新
- 週間ダウンロード数が急増または急減したパッケージ(乗っ取りのシグナル)
低リスクカテゴリは自動化で効率化する:
- 信頼済みパッケージのパッチ更新(ホワイトリスト制御)
- devDependenciesの更新(本番には影響しない)
- 冷却期間 + CI全通過 + SCAスキャン通過の3条件を満たすもの
人間のレビューは「依存関係の変更が何をするのかを理解する」という認知的なプロセスだ。変更されたパッケージのCHANGELOGを確認する、postinstallスクリプトが追加されていないか確認する、パッケージの週間ダウンロード数とGitHubの星の数に急変がないか確認する——これらは自動化ツールが代わりにできない判断だ。
(公開後3-7日)"] B --> C["Layer 2: SCAスキャン
(Socket.dev / OSV)"] C --> D["Layer 3: CI/テスト通過"] D --> E{"高リスク
カテゴリ?"} E -->|"Yes(GitHub Actions
/ secrets access
/ major update)"| F["🧑 人間レビュー必須
CHANGELOGと差分確認"] E -->|"No(whitelist内
パッチ・マイナー)"| G["✅ 自動マージ可"] F --> H{"承認?"} H -->|"Yes"| G H -->|"No / 不審"| I["❌ マージ拒否
セキュリティチームへ報告"]
Renovate・DependabotはOSSエコシステムを健全に保つ重要なインフラだ。しかし今やそれらは攻撃者のターゲットでもある。冷却期間・SCAツール・ハニートークンを組み合わせた多層防御は攻撃の成功確率を大幅に下げるが、すべてのレイヤーを通過した更新に対して最後に人間の目を通すゲートキーパー設計こそが、2026年以降のサプライチェーンセキュリティの本質だ。
自動化への信頼と人間のレビューのバランスをどこに引くか——その判断こそが、あなたのチームが持つべき最も重要なセキュリティポリシーだ。
参照ソース
- Renovate & Dependabot: The New Malware Delivery System - GitGuardian Blog
- Renovate公式ドキュメント: minimumReleaseAge設定
- Dependabot security updates - GitHub Docs
- Keeping your GitHub Actions and workflows secure - GitHub Security Lab
- Supply-chain Levels for Software Artifacts (SLSA) Framework
- npm audit documentation