展開失敗のデバッグ:一般的なYAMLと設定のエラーを特定する
Kubernetesへのアプリケーションのデプロイは、YAMLマニフェストを介して管理される宣言型設定によって効率化されることがよくあります。しかし、デプロイが目的の状態に達せず、Pending、ImagePullBackOffで停止したままになったり、突然失敗したりする場合、その根本原因は、これらの設定ファイルまたは基盤となるクラスターリソース内の些細なエラーにあることがよくあります。このガイドでは、Kubernetesデプロイを悩ませる一般的なYAMLおよび設定の落とし穴を診断し、解決するための体系的なアプローチを提供します。
Kubernetesイベントを解釈し、リソースの状態を検査する方法を理解することは、効率的なデバッグのために不可欠です。この記事では、構文エラー、リソース制約、ネットワーク設定の問題に焦点を当て、失敗したデプロイを健全な稼働状態に迅速に移行させるために必要な必須のコマンドとチェックについて説明します。
最初のステップ:デプロイの状態とイベントの確認
デプロイが失敗した場合、最初の診断ステップは、常にプライマリリソース自体と、それが管理するReplicaSetおよびPodに関連するイベントを確認することです。これにより、Kubernetesが何をしようとしていて、なぜ失敗しているのかについて、最も高レベルの視点が得られます。
1. デプロイの健全性の検査
kubectl get deployments を使用して、全体的な状態を確認します。特に、READY、UP-TO-DATE、AVAILABLE の各列に注目してください。ここに不一致がある場合、基盤となるPodに問題があることを示しています。
kubectl get deployments <deployment-name>
デプロイの状態が準備完了レプリカが少ない、またはゼロの場合、ReplicaSetの確認に進みます。
2. ReplicaSetとPodのイベントの確認
ReplicaSetは、Podの希望する数を管理します。デプロイが失敗した場合、ReplicaSetがエラーのカスケードの発生源であることがほとんどです。ReplicaSetに対して describe コマンドを使用します。通常、<deployment-name>-<hash>という名前です。
kubectl describe rs <replicaset-name>
重要なのは、出力の下部にある Events セクションを調べることです。このセクションには、スケジューリング試行、イメージプル失敗、ボリュームマウントの問題など、最近のアクションが詳細に記載されています。これらのイベントが、しばしば決定的な証拠となります。
最後に、Pod自体を確認します。Podが即時の失敗を報告するためです。
kubectl get pods -l app=<your-app-label>
kubectl describe pod <pod-name>
Podの説明にある State と Reason フィールドを探します。一般的な理由には、ImagePullBackOff、ErrImagePull、CrashLoopBackOff、Pending があります。
YAMLマニフェストにおける一般的な設定エラー
YAMLファイルの設定ミスは、デプロイ失敗の最も頻繁な原因です。これらのエラーは、単純なインデントミスから複雑な構造上の問題まで多岐にわたります。
1. YAMLの構文と構造のエラー
Kubernetes APIは、正しいYAML構文(インデント、スペース、データ型)に非常に敏感です。YAMLが無効な場合、kubectl applyはファイルを解析できないと報告して、すぐに失敗することがよくあります。
ベストプラクティス:リンターの使用
適用する前に、必ずYAML構文を検証してください。yamllint や統合IDEのサポートなどのツールは、基本的な構文エラーをすぐに検出できます。
一般的な構造エラーの例: マッピングまたはインデントの誤り。
# INCORRECT indentation for container port
containers:
- name: my-app
image: myregistry/myapp:v1
ports:
- containerPort: 8080 # Should be indented under the list item '-'
2. イメージ参照とプルエラー
PodがImagePullBackOffまたはErrImagePullになる場合、問題はコンテナイメージへのアクセスに関連しています。
- イメージ名/タグのタイプミス: イメージリポジトリ、名前、およびタグのスペルを再確認してください。
- プライベートレジストリ認証: プライベートレジストリ(Docker HubプライベートリポジトリやECR/GCRなど)からプルする場合、Pod仕様で
ImagePullSecretを正しく設定し、参照していることを確認してください。
# Snippet showing ImagePullSecret usage
spec:
imagePullSecrets:
- name: my-registry-secret
containers:
# ... rest of container spec
3. リソース要求と制限の違反
PodがPending状態のままで、イベントにリソース不足が言及されている場合、クラスターノードはYAMLで定義されたCPUまたはメモリ要件を満たすことができません。
デプロイマニフェストで指定された制限を確認してください。
resources:
requests:
memory: "512Mi"
cpu: "500m"
limits:
memory: "1Gi"
cpu: "1"
トラブルシューティングの手順:
1. kubectl describe nodes を使用して、利用可能な容量を確認します。
2. 0/3 nodes are available: 3 Insufficient cpu のようなイベントが表示される場合、YAMLのrequestsを減らすか、クラスターにノードを追加する必要があります。
高度な設定の問題
基本的な構文やイメージのプル以外にも、ネットワーク、ストレージ、スケジューリングを含む複雑な設定は、診断が困難な失敗につながる可能性があります。
1. プローブ(LivenessおよびReadiness)の設定ミス
PodがCrashLoopBackOffに移行する場合、コンテナが起動してもすぐにチェックに失敗するか、起動してもReadinessプローブに繰り返し失敗することを意味することがよくあります。
- Liveness Probe: これが失敗すると、Kubernetesはコンテナを再起動します。アプリケーションログ(
kubectl logs <pod-name>)を確認して、クラッシュする理由を特定します。 - Readiness Probe: これが失敗すると、PodはServiceのエンドポイントから除外されます。パス、ポート、および予期される応答コードが、アプリケーションが実際に提供しているものと一致していることを確認してください。
一般的なReadiness Probeエラーの例: 間違ったポートをターゲットにしている、またはアプリケーションがTCPのみを公開しているのにHTTPを期待している場合。
2. ボリュームおよびPersistentVolumeClaim(PVC)の失敗
ボリュームの問題によりPodがペンディング状態の場合、PVCの状態を検査します。
kubectl get pvc <pvc-name>
PVCの状態がPendingの場合、クラスターが一致するStorageClassまたはバインドするのに適したPersistentVolumeを見つけられなかったことを意味します。PVCイベントで特定のバインディングエラーを確認してください。
3. アフィニティおよびアンチアフィニティルール
nodeAffinityやpodAntiAffinityのような複雑なスケジューリングルールは、すべての条件を満たすノードがない場合、意図せずPodのスケジューリングを妨げる可能性があります。PodがPendingのままで、イベントにスケジューリングの制限が言及されている場合、これらのルールを見直してください。
例えば、既存のどのノードも持っていない特定のラベル(nodeSelector)を持つノードでPodを実行する必要がある場合、そのPodは決してスケジューリングされません。
# Example: Restricting deployment to nodes labeled 'disktype: ssd'
spec:
nodeSelector:
disktype: ssd
containers:
# ...
トラブルシューティングのヒント: 制限的なnodeSelectorまたはaffinityルールを一時的にコメントアウトします。Podが正常にスケジューリングされる場合、問題が選択基準にあることがわかります。
デバッグワークフローの要約
デプロイの失敗に直面した場合、以下の構造化されたパスに従ってください。
- デプロイの状態:
kubectl get deployments-> レプリカは準備完了を報告していますか? - Podイベント:
kubectl describe pod <failing-pod>-> Events セクションで即時のエラー(ImagePull、OOMKilled、ボリュームの問題)を確認します。 - コンテナログ:
kubectl logs <failing-pod>-> コンテナが起動してもクラッシュする場合(CrashLoopBackOff)、アプリケーションロジックまたはLivenessプローブが疑われます。 - リソースチェック: Podが
Pendingの場合、リソース制約(Insufficient cpu/memory)またはボリュームバインディングの失敗(PVCステータス)を確認します。 - 設定の検証: インデント、正しいフィールド名、有効なリソース値(要求/制限)についてYAMLを確認します。
状態、イベント、および基盤となるYAML設定をKubernetesの期待値と照らし合わせて体系的に確認することで、ほとんどのデプロイ失敗の根本原因を迅速に特定し、解決することができます。