問題の概要
Kubernetes の内部サービスにアクセスするための定番ツールといえば kubectl port-forward です。シンプルで効果的ですが、ターゲットとなる Pod が完全に起動していない場合、コマンドはすぐに失敗し、次のようなフラストレーションの溜まるエラーが表示されます。
error: unable to forward port because pod is not running. Current status=Pending
根本的な原因は単純です。kubectl がネットワークトンネルを確立するには、アクティブで実行中のコンテナが必要です。Pod が Pending 状態のまま動かない場合、コンテナはまだノード上に存在すらしていないため、コマンドの接続先がない状態になります。
TL;DR: 迅速な解決策
- Pod の状態を確認:
kubectl get pods - 原因を調査:
kubectl describe pod <pod-name> - 下部にある Events セクションを確認します。
- リソースまたはイメージの問題を修正し、
Running状態になるまで待ちます。
ステップバイステップのトラブルシューティング
1. Pod のステータスを確認する
まずは、どの Pod がプロセスを止めているのかを特定しましょう。次のコマンドを実行します。
kubectl get pods
おそらく、次のような出力が表示されます。
NAME READY STATUS RESTARTS AGE
web-api-7444d589-abcde 0/1 Pending 0 4m
ステータスが Pending、ContainerCreating、または ImagePullBackOff である限り、ポートフォワードのトンネルは確立できません。1/1 READY と表示される必要があります。
2. Pod のイベントを調査する
Pending 状態はあくまで症状に過ぎません。実際のボトルネックを見つけるには、Pod の詳細を表示して内部ログを確認します。
kubectl describe pod web-api-7444d589-abcde
この出力の中で最も重要なのが Events セクションです。ここでは Kubernetes スケジューラが失敗の理由を説明しています。よくある以下の警告サインを探してください。
FailedScheduling: クラスターに十分な空き CPU または RAM を持つノードがありません。ErrImagePull: イメージ名のスペルミス、またはレジストリにログインシークレットが必要です。NetworkPlugin cni config not initialized: ノードのネットワークレイヤーが壊れています。
3. Pending 状態の一般的な修正方法
シナリオ A: リソース不足
イベントログに 0/3 nodes are available: 3 Insufficient cpu と表示されている場合、クラスターの容量がいっぱいです。たとえば、Pod が 500m (0.5 CPU) を要求しているのに、ノードに 200m しか空きがない場合、Pod は永久に Pending 状態のままになります。これを解決するには、以下の方法があります。
- Deployment YAML の
resources.requestsを下げます。 - ノードを追加してクラスターを拡張します。
- 未使用の Pod を削除してリソースを回収します。
シナリオ B: イメージの問題
ImagePullBackOff が表示されたら、すぐにイメージのパスを確認してください。Docker Hub や AWS ECR などのプライベートレジストリを使用している場合は、Pod スペックに imagePullSecrets が定義されているか確認します。イメージタグのわずかなタイポ(例:v1.2.1 ではなく v1.2.0)でもデプロイは停止します。
シナリオ C: ノードのネットワーク制限
ノードで使用可能な IP アドレスが枯渇しているため、Pod が Pending のままになることがよくあります。これは、小さなサブネットを使用している AWS EKS などのクラウド環境で頻繁に発生します。たとえば、/28 サブネットでは 16 個の IP アドレスしか提供されません。これらが使い果たされると、スケジューラは新しい Pod に IP を割り当てることができません。私は IP Subnet Calculator を使用して、CIDR ブロックが予定している規模に対して十分な大きさであることを確認しています。
待機と確認
根本的な原因を解決したら、Pod が Running に移行するまで監視します。
kubectl get pods -w
ステータスが Running になり、READY 列が 1/1 になったら、ポートフォワードのコマンドを再開します。
kubectl port-forward deployment/web-api 8080:80
予防のためのヒント
- Deployment に対してフォワードする: 特定の Pod 名に対してポートフォワードしないでください。代わりに
kubectl port-forward deployment/my-app 8080:80を使用します。1つの Pod が Pending でも別の Pod が Running であれば、Kubernetes は自動的に健全な Pod へルーティングします。 - 現実的なリクエストを設定する: 必要以上に高いリソースリクエストを設定しないでください。2 CPU しかないマシンに 4 CPU をリクエストすると、Pod は決して起動しません。
- Liveness Probe を確認する:
readinessProbeが失敗していないか確認してください。Pod が「Running」であっても「Ready」でない場合、ネットワークトラフィックが遮断されることがあります。

