Dockerfileの危険性:1つのCOPY命令がコンテナを危険にさらす

急速に進化するコンテナ化の世界では、Dockerはアプリケーション展開の標準となっています。しかし、安全性への懸念が高まる中、Dockerの利用増加に伴い、ベースイメージの脆弱性、実行時攻撃、設定ミスなどのリスクも増加しています。多くの開発者は実行時のセキュリティやネットワーク設定に注力していますが、最も重要な脆弱性はDockerfileそのものに潜んでいることが多く、誤ったCOPY命令一つで重大なセキュリティ侵害が起こり得ます。
最近のセキュリティアドバイザリは、Dockerfileをセキュリティ上重要なコードとして扱う必要性を強調しています。Docker Desktop上で悪意のあるコンテナが稼働すると、Docker Engineにアクセスし、Dockerソケットをマウントせずに追加のコンテナを起動できる可能性があります。これにより、ホストシステム上のユーザーファイルに不正アクセスされる恐れがあり、CVE-2025-9074が示すように、基盤となるセキュリティの前提が崩れる危険性があります。
Dockerfileに潜む隠れた脆弱性
コンテナレイヤーの欺瞞
Dockerfileの各命令は、新しいレイヤーを作成します。この層構造はキャッシュや配布に効率的ですが、ビルド中のすべての操作の監査証跡となります。たとえ後の命令でファイルを削除しても、中間層に残存し続け、秘密情報や敏感なデータが永続的に画像履歴に埋め込まれる可能性があります。
以下のようなDockerfileのスニペットを考えてみてください:
FROM node:18-alpine
WORKDIR /app
COPY package*.json ./
RUN npm install
COPY .env ./
RUN chmod +x deploy.sh && ./deploy.sh
RUN rm .env
COPY . .
CMD ["npm", "start"]
RUN rm .env命令にもかかわらず、.envファイルはCOPY .env ./で作成されたレイヤーに残っています。攻撃者はDockerコマンドやイメージ解析ツールを使ってこのレイヤーを抽出し、開発者が安全だと考えていた認証情報を取得することが可能です。
マルチステージビルドの汚染
マルチステージビルドは、軽量で安全なイメージを作るための強力な機能です。ビルド命令を複数のステージに分割し、必要なファイルだけを最終イメージに含めることができます。ただし、誤った実装は高度なサプライチェーン攻撃のベクトルとなり得ます。
COPY --from命令は、ビルドステージ間でアーティファクトをコピーするために使われますが、外部イメージや汚染された依存関係を持つステージを参照すると、意図しない内容が混入する可能性があります。例:
FROM node:18 as builder
RUN npm install -g suspicious-build-tool
COPY . .
RUN npm run build
FROM nginx:alpine
COPY --from=builder /app/dist /usr/share/nginx/html
suspicious-build-toolパッケージに悪意のあるコードが含まれている場合、ビルドアーティファクトにバックドアを仕込むことができ、最終的なイメージに潜む脅威となります。見た目はクリーンで最小限に見えますが、ビルド中に起きた侵害を隠しています。
ベースイメージの信頼性問題
すべてのコンテナ化されたアプリケーションは、FROM命令で指定されたベースイメージに依存しています。しかし、多くの開発者はベースイメージの選択を単なる技術的決定とみなしており、セキュリティ上の重要な判断を怠っています。公開されたイメージの中には、数百万ダウンロードされていても、マルウェアやバックドア、脆弱なソフトウェアが事前に仕込まれているケースがあります。
Docker Hubの人気イメージの分析では、公式と見なされるイメージの30%以上に高重大度の脆弱性が含まれており、不必要なパッケージも多く含まれ、攻撃面を拡大しています。python:latestのような便利なイメージを使う際も、その構成を理解せずに利用すると、意図した機能だけでなく潜在的なセキュリティリスクも引き継ぐことになります。
COPY命令を利用した高度な攻撃ベクトル
ビルドコンテキストを利用した秘密情報の注入
COPY命令のセキュリティは、単に敏感なファイルをコピーするだけにとどまりません。docker buildを実行するディレクトリ内のすべての内容がビルドコンテキストとして利用されるため、不注意なディレクトリ構造や.dockerignoreの設定次第で、秘密情報が含まれることがあります。
特に、ビルド引数や環境変数を使った攻撃は次のように行われます:
FROM ubuntu:20.04
ARG SECRET_KEY
COPY --chown=www-data:www-data config/${SECRET_KEY}.conf /etc/app/
このパターンは、一見安全に見えますが、SECRET_KEYの値が画像のメタデータに永続的に埋め込まれ、外部入力により意図しないファイルをコピーされるリスクがあります。
シンボリックリンクの悪用とパストラバーサル
COPY操作時のシンボリックリンクの扱いは、意図しないファイルアクセスにつながることがあります。ビルドコンテキストに外部のディレクトリを指すシンボリックリンクが含まれると、COPY命令はこれらのリンクをたどり、ホストシステムのファイルをコンテナに取り込む可能性があります。
攻撃者はCI/CDパイプラインの侵害などを通じて、次のようなシンボリックリンクを作成できます:
ln -s /etc/passwd ./innocent-looking-file.txt
ln -s /home/user/.ssh/id_rsa ./public-key.txt
これらのリンクを含むCOPY . /app/命令は、ホストの敏感なファイルを無意識にコンテナに取り込み、誰でもアクセスできる状態にします。
マルチステージビルドのセキュリティパラドックス
共有依存関係のリスク
マルチステージビルドは、最終イメージのサイズ削減に優れていますが、複数のステージで同じ汚染されたベースイメージやリポジトリを使うと、脆弱性が共有されるリスクがあります。例として、ビルドと本番の両方で同じリポジトリからパッケージを取得し、その中に脆弱なコードが含まれている場合です。
FROM python:3.9 as builder
RUN pip install build-tools==1.0.0
COPY requirements.txt .
RUN pip wheel --no-cache-dir -r requirements.txt
FROM python:3.9-slim
COPY --from=builder /wheels /tmp/wheels
RUN pip install --find-links /tmp/wheels app-dependencies
build-toolsやrequirements.txtに含まれる依存パッケージに悪意のあるコードがあれば、最終的なホイールに不正なコードが注入され、運用環境に展開される危険があります。
継承チェーン攻撃
攻撃者は、巧妙に作り込まれたベースイメージを利用し、継承の仕組みを悪用します。見た目は正当なイメージに見えながら、微妙なバックドアを仕込み、下流の多くのイメージに影響を及ぼすことが可能です。
例:
# 悪意のあるベースイメージには隠されたロジックが含まれる
FROM malicious/node:18-alpine
# 通常のアプリビルド
COPY package.json .
RUN npm install
COPY app.js .
# 悪意のあるベースイメージは、app.jsを検知して隠された機能を起動
レイヤー分析とフォレンジック脆弱性
永続的なメモリ問題
Dockerのレイヤードファイルシステムは、「永続的メモリ」と呼ばれる、削除コマンド後もアクセス可能なデータを生成します。秘密情報や資格情報は、Dockerfileの命令(環境変数、args、コマンド内にハードコーディングされたもの)に絶対に含めないこと。特に、コピーされるファイルには注意が必要です。
各レイヤーはファイルシステムの変更履歴を完全に保持しており、早期にコピーされた敏感なデータは、イメージの寿命を通じてフォレンジック的に回収可能です。現代のコンテナ解析ツールは、ファイル操作の履歴を再構築し、開発者が安全だと考えた情報漏洩を明らかにします。
この問題は、コンテナレジストリの配布とキャッシュの仕組みにより、複数のシステムにわたり長期間にわたって脆弱性が残ることも意味します。
レジストリによる攻撃拡大
コンテナレジストリは、Dockerfileの脆弱性の伝播を加速させる役割も果たします。脆弱なイメージをレジストリにプッシュすると、多くの信頼されたユーザーがそれを利用し続けることになります。
キャッシュのタイミングに依存するため、脆弱性修正後も古いキャッシュが流通し続け、長期にわたりリスクが残ることがあります。
安全なDockerfileの構築パターン
ゼロトラストビルドコンテキストの実現
ゼロトラストの考え方では、ビルドコンテキストのすべての要素を潜在的に危険とみなします。.dockerignoreを厳格に設定し、必要最小限のファイルだけを含める構成にします。ビルドに必要な情報だけを提供し、不要なファイルや秘密情報は含めないことが重要です。
また、環境変数やDocker secrets、BuildKitを利用して安全に情報を扱います。これらの方法は、それぞれのセキュリティ要件と運用状況に応じて使い分けてください。
マルチステージのセキュリティ分離
各ステージをセキュリティ境界として扱うことが重要です。具体的には:
- ビルドと本番用のベースイメージを分離
- 各ステージ間での依存関係スキャンを実施
- BuildKitのシークレットマウント機能を活用
- 途中検証ステージを設けて、コピーしたアーティファクトの整合性を確認
BuildKitのシークレット管理
BuildKitは、ネイティブのシークレット管理機能を提供し、多くの伝統的なCOPYに基づくリスクを排除します:
# syntax=docker/dockerfile:1
FROM python:3.9-slim
# シークレットマウントを利用
RUN --mount=type=secret,id=api_key \
curl -H "Authorization: Bearer $(cat /run/secrets/api_key)" \
https://api.example.com/secure-data | process_data
# シークレットはファイルシステムに書き込まれません
COPY app.py /app/
この方法により、敏感な情報はイメージのレイヤーに残らず、ビルド時に必要なときだけアクセスされます。
検出と対策
自動Dockerfileセキュリティスキャン
静的解析ツールを用いて、セキュリティリスクを検出します。特に以下に注意してください:
- ハードコーディングされた秘密情報
- 危険なCOPYパターン
- 信頼できないベースイメージ
- マルチステージのセキュリティ境界違反
実行時の検知
既知のコンテナエスケープ脆弱性に対抗するため、ホストとDockerのアップデートは必須です。監視システムは次の点を追跡します:
- 予期しないネットワーク接続
- アプリケーションの想定外のファイルアクセス
- バックドア活動を示すプロセス実行
- コンテナとホスト間の通信試行
緊急対応手順
侵害が検出された場合は、次の対応を行います:
- すべてのレジストリから侵害イメージを即座に削除
- 関係者とシステムに通知
- 侵害されたレイヤーと配布履歴のフォレンジック分析
- 検証済みビルドを用いたクリーンなイメージの再構築
Dockerfileセキュリティの未来
新たな標準と実践
コンテナセキュリティのコミュニティは、新しい安全な構築基準を策定中です。例:
- ベースイメージのサプライチェーン証明
- Dockerfile命令の暗号署名
- SBOM(ソフトウェア部品表)生成との連携
- デフォルトのゼロトラストネットワーク
技術の進化
今後のDockerには、次のようなセキュリティ強化が期待されます:
- ビルド時のシークレットスキャンの義務化
- ビルドステージ間の隔離強化
- すべてのCOPY操作の監査ログ
- 外部セキュリティスキャンサービスとの連携
結論:Dockerfileはセキュリティ上重要なコードとして扱う
たった一つのハッキングされたコンテナが、機密情報を漏洩させたり、アクセス権を拡大したり、システム全体を破壊したりする可能性があります。証拠は明白です:Dockerfileは、重要なインフラコードと同じ厳格さで扱う必要があります。
Dockerfileに潜む脆弱性は非常に巧妙で、ランタイム攻撃のように監視システムをトリガーしません。むしろ、アプリケーション展開の根幹に潜み、気付かぬうちに被害を拡大します。
組織は、単なる展開の便利さから、セキュリティの重要な要素としてDockerを位置付ける必要があります。これには、包括的なDockerfileのセキュリティレビュー、自動スキャン、そしてすべてのCOPY命令を潜在的な攻撃ベクトルとみなすことが含まれます。
今後の道は、より良いツール、強化されたDockerの機能、拡張されたスキャン能力といった技術的解決策と、セキュリティ意識を開発のあらゆる側面に浸透させる文化的変革の両輪によって進められます。Dockerfileの隠れた危険を認識し対処することで、真に安全なコンテナ化アプリケーションを構築できるのです。
コンテナ化が現代ソフトウェア展開の主流となる中、Dockerfileのセキュリティリスクは増す一方です。Dockerfileは、あなたのアプリケーションの構築過程のドキュメントです。攻撃者もあなたの開発チームと同じようにそれを読むことができることを忘れずに。セキュリティを語るストーリーにしてください。
Related InstaTunnel pages
Continue from this article into the most relevant product guides and workflows.
Related Topics
Keep building with InstaTunnel
Read the docs for implementation details or compare plans before you ship.