問題:なぜプルがタイムアウトするのか
docker pullと入力してEnterを押し、待ちます。通常のプログレスバーが表示される代わりに、ターミナルは60秒間沈黙します。最終的に、タイムアウトメッセージが表示されて終了します。
Error response from daemon: Get "https://registry-1.docker.io/v2/": context deadline exceeded
本質的には、Docker内部のストップウォッチがゼロになったことを意味します。公式レジストリに接続しようとしましたが、ネットワークの応答が十分に速くありませんでした。これは通常、Docker自体のバグではありません。企業内ファイアウォール、低速なDNS、または誤ったネットワークブリッジの設定による「話し中」のような状態だと考えてください。
デバッグ手順:ボトルネックの特定
やみくもに設定を変更し始めるのはやめましょう。まずは、どこで信号が途切れているのかを正確に見つけます。以下のチェックを行い、原因を特定してください。
1. 基本的な接続性の確認
マシンがレジストリを認識できていますか?Docker Hub APIへの接続をテストします:
ping registry-1.docker.io
ミリ秒単位の時間を確認してください。レイテンシが500msを超える場合、Dockerのデフォルトのハンドシェイクには接続が遅すぎます。「unknown host」と表示される場合は、システムがドメインを完全に認識できていません。
2. DNS速度のテスト
プロバイダー(ISP)提供のDNSサーバーは、速度が遅かったり、レジストリドメインを断続的にブロックしたりすることで知られています。nslookupを使用して、解決にどれくらい時間がかかるか確認します:
nslookup registry-1.docker.io
このコマンドがIPアドレスを返すのに2秒以上かかる場合、Dockerはダウンロードが始まる前にほぼ確実にタイムアウトします。
「Context Deadline Exceeded」の確実な修正方法
解決策1:高速なDNSへの切り替え
最も効果的な修正方法は、Dockerの参照先をGoogle(8.8.8.8)やCloudflare(1.1.1.1)に向けることです。OS全体の設定を変更する必要はありません。Dockerデーモンにのみ適用できます。
/etc/docker/daemon.jsonを開くか作成し、DNS配列を追加します:
{
"dns": ["1.1.1.1", "8.8.8.8"]
}
サービスを再起動して変更を適用します:
sudo systemctl restart docker
解決策2:プロキシ設定の構成
企業内プロキシの背後で作業している場合、Dockerに対して明示的にトラフィックのルーティング方法を伝える必要があります。シェルのEXPORT変数は自動的には引き継がれません。systemdサービスを直接設定する必要があります。
- 専用の設定ディレクトリを作成します:
sudo mkdir -p /etc/systemd/system/docker.service.d
- プロキシの詳細を記述した`http-proxy.conf`を作成します:
```
[Service]
Environment="HTTP_PROXY=http://proxy.yourcompany.com:8080/"
Environment="HTTPS_PROXY=http://proxy.yourcompany.com:8080/"
Environment="NO_PROXY=localhost,127.0.0.1"
- 設定をリロードしてDockerを再起動します:
sudo systemctl daemon-reload sudo systemctl restart docker
### 解決策3:MTU不一致の修正(VPNユーザー向け)
VPNを使用していますか?ネットワークパケットが暗号化トンネルに対して大きすぎる可能性があります。パケットが大きすぎると破棄され、ダウンロード開始時に謎のハングアップが発生します。
標準のMTUは1500です。`daemon.json`で1450に下げて、パケットに「余裕」を持たせてみてください:
{ "mtu": 1450 }
### 解決策4:ローカルレジストリミラーの使用
お住まいの地域からDocker Hubの米国ベースのサーバーへの接続が悪い場合は、より近いミラーを使用してください。これにより、長距離ルーティングの問題を回避できます。これを`daemon.json`に追加します:
{ "registry-mirrors": ["https://mirror.gcr.io"] }
## 検証:修正のテスト
小さなイメージをプルして動作を確認します。500MBのデータベースをプルして時間を無駄にしないでください。わずか5MB程度の`alpine`を使用します:
docker pull alpine:latest
レイヤーがすぐにダウンロードされれば、ボトルネックは解消されています。
## プロのヒント:ネットワークの重複を避ける
Dockerの内部ネットワーク(172.17.0.0/16など)が、オフィスの実際のIP範囲と重複しているためにタイムアウトが発生することがあります。インフラを計画する際、[IPサブネット計算機](https://toolcraft.app/en/tools/developer/ip-subnet-calculator)を使用すると、ローカルルーティングと競合しない安全な範囲を選択するのに役立ちます。これにより、デバッグが非常に困難な「ゴースト」接続問題を未然に防ぐことができます。
## クイックまとめ
- **DNSが第一容疑者:** 名前解決の遅延が、これらのエラーの90%の原因です。
- **Daemon JSONを活用する:** ほとんどのネットワーク修正は`/etc/docker/daemon.json`で行います。
- **プロキシは別設定:** Dockerはサービスとして動作するため、独自のsystemdプロキシ設定が必要です。
- **VPNではMTUが重要:** 小さなpingは通るのに大きなプルが失敗する場合は、MTUを1400または1450に下げてください。

