HOMEデベロッパー向け ブログ・コミュニティ SCSK技術者ブログ OpenShiftでPodが起動してReadyになるまで|内部処理を5ステップで解説
OpenShiftでPodが起動してReadyになるまで|内部処理を5ステップで解説
みなさん、こんにちは。Red Hat OpenShiftの構築を担当している巻島です。
この記事では、Podが作成されてから、アプリケーションが通信を受け付けられるReady状態になるまでの流れを整理して説明します。
「どの機能が何をするのか」と「起動処理がどこで止まっているのか」を理解することが目的となります。
1. 「Podの起動」とは
Podの起動には、複数の段階があります。画面にRunningと表示されても、アプリケーションがトラフィックを受け付けられるReady状態になっているとは限りません。Podがどこまで起動しているかは、主に次のPod Conditionで確認できます。
| Condition(状態情報) | 意味 |
|---|---|
| PodScheduled | Podが実行先Nodeへ割り当てられた |
| PodReadyToStartContainers | Pod sandboxとネットワークの準備が完了し、コンテナを作成できる |
| Initialized | 通常のinitコンテナがすべて正常終了した |
| ContainersReady | Pod内のすべてのコンテナがReadyになった |
| Ready | 全コンテナとreadinessGatesの条件を満たし、リクエストを処理できると判定された |
Runningは、PodがNodeに割り当てられ、すべてのコンテナが作成され、少なくとも一つのコンテナが実行中、起動中、または再起動中であることを示します。
そのため、Readiness Probeに失敗している場合は、STATUSがRunningでも、READY欄は0/1のままです。
用語メモ
- Pod Condition:Podが起動処理の各段階を通過したかを示す状態情報
- ReadinessGates:Pod独自の追加のReady条件
2. 全体像
Pod作成からReadyまでの流れを、コントロールプレーンとワーカーノードに分けると次のようになります。
図:Pod作成からReadyまでの流れ
配置先が決まると、そのNodeのkubeletが、Volume、ネットワーク、イメージなどの準備を調整します。CRI-Oは、kubeletからの依頼を受けてコンテナの作成や起動を行います。
OpenShiftの標準構成では、Podネットワークの設定にOVN-Kubernetesが関わります。OVN-Kubernetesは、OpenShift Container Platformの標準ネットワークプロバイダーです。
用語メモ
- OVN-Kubernetes:PodやService間のネットワークを管理する仕組み
3. PodがReadyになるまでの5ステップ
Step 1. Podを作成し、Nodeを決める
DeploymentなどのコントローラーがPodオブジェクトをAPI Serverへ作成します。Schedulerは未割り当てのPodを見つけ、必要とするCPUやメモリーやNodeへの配置条件、Pod同士の配置条件、Volumeの利用条件などを確認してNodeを選びます。配置先が決まるとPodScheduled=Trueになります。
Step 2. kubeletが起動の準備をする
配置先Nodeのkubeletが、自分のNodeに割り当てられたPodを検知します。
kubeletは最初に、Podが使用するVolumeを準備します。その後、CRIを通じてCRI-OへPod sandboxの作成を依頼します。
CRI-Oは、OVN-Kubernetesなどのネットワーク機能と連携し、Podのネットワークを設定します。Pod sandboxの作成とネットワーク設定が完了すると、PodReadyToStartContainers=True
となります。その後、必要なコンテナイメージがNodeにない場合は、CRI-Oがレジストリからイメージを取得します。イメージを取得できない場合は、ErrImagePullやImagePullBackOffが表示されます。
用語メモ
- kubelet:各Node上でPodの起動や状態確認を行うプログラム
- CRI:kubeletとコンテナ実行基盤をつなぐインターフェース
- CRI-O:コンテナの作成・起動・停止などを行う実行基盤
- Pod sandbox:同じPod内のコンテナが共有するネットワークなどの土台
Step 3. initコンテナを実行する
通常のinitコンテナが定義されている場合、Podの定義に書かれた順番で一つずつ実行されます。先のinitコンテナが正常終了するまで、次のinitコンテナは開始されません。すべて正常終了するとInitialized=Trueになり、アプリケーションコンテナの起動へ進みます。
用語メモ
- initコンテナ:アプリケーション本体を起動する前に、設定やデータの準備を行うコンテナ
Step 4. アプリケーションコンテナを起動する
CRI-Oがコンテナを作成し、Node上でアプリケーションプロセスを開始します。この段階でPod phaseがRunningになることがあります。ただし、Runningはアプリケーションが利用可能になったことを保証しません。アプリケーションの初期化処理が続いていたり、Readiness Probeに失敗していたりする可能性があります
Step 5. ProbeでReadyを判定する
kubeletは設定されたProbeを実行します。Startup Probeは起動完了、Readiness Probeは通信を受けられるか、Liveness Probeは再起動が必要な異常かを確認します。すべてのコンテナがReadyになり、追加のReady条件(readinessGates)がある場合はそれも満たすと、Ready=Trueになります
| Probe | 役割 |
|---|---|
| Startup | アプリケーションの起動完了を確認する |
| Readiness | トラフィックを受けられるかを判定する |
| Liveness | 異常時にコンテナを再起動するか判断する |
用語メモ
- Probe:kubeletがコンテナの状態を確認するためのチェック
- Service:複数のPodに対して、安定した接続先を提供する仕組み
4. 起動が止まった箇所の判別方法
STATUSだけで判断せず、oc describe podのEventsとPod Conditionを合わせて確認します。
| 見える状態 | 主に確認する場所 |
|---|---|
| Pending / PodScheduled=False | CPU・メモリーのrequests、Nodeの配置条件、PVC、Events |
| ContainerCreating | Volume、Pod sandbox、OVN-Kubernetes、Events |
| ImagePullBackOff | イメージ名、imagePullSecret、レジストリ接続 |
| Init:0/N、Init:Error | initコンテナのログ、終了コード、依存先 |
| STATUS=Running、READY=0/1 | Startup / Readiness Probe、アプリケーションの起動状態 |
| CrashLoopBackOff | 直前のログ、起動コマンド、環境変数、終了コード |
5. まとめ
- Schedulerは、Podを実行するNodeを決める
- 配置先Nodeのkubeletが、Volumeやネットワークなどの準備を調整する
- CRI-Oが、Pod sandboxやコンテナの作成・起動を行う
- 通常のinitコンテナが完了した後、アプリケーションコンテナが起動する
- RunningとReadyは同じではない
- 起動障害では、「配置先の決定 → 起動準備 → initコンテナ → アプリケーション → Ready判定」のどこで止まっているかを確認する
Podの起動を確認するときは、STATUS欄のRunningだけを見るのではなく、Readiness ProbeとReady Conditionまで確認することが重要です。
参考文献
[1]https://docs.redhat.com/en/documentation/openshift_container_platform/4.22/
[2]https://kubernetes.io/docs/concepts/workloads/pods/pod-lifecycle/
[3]https://kubernetes.io/docs/concepts/workloads/pods/probes/
[4]https://kubernetes.io/docs/concepts/workloads/pods/init-containers/