はじめに
kubelet は、各 Node で Pod を実行・管理する Kubernetes のコンポーネントです。コンテナの起動だけでなく、Probe の実行、Volume のマウント、Node の状態報告、リソース不足時の Pod の退避、ログのローテーションなども担当しています。
Pod が起動しない、Node が NotReady になる、ディスクが不足するといった問題では、kubelet の複数の機能が関係します。この記事では、kubelet の主な機能を一覧にし、それぞれの役割と、設定・メトリクスの対応を整理します。
対象コンポーネントとバージョン
| コンポーネント | バージョン | リポジトリ | 本記事での役割 |
|---|---|---|---|
| kubelet | v1.37.1 | kubernetes/kubernetes | 機能・設定・メトリクスの確認対象 |
Linux Node を中心に説明します。設定のデフォルト値は、特記しない限り KubeletConfiguration (kubelet.config.k8s.io/v1beta1) の値です。kubeadm やマネージド Kubernetes が設定する値とは異なる場合があります。
TL;DR
- kubelet は Node 上で Pod を実行・管理します。 自分の Node に割り当てられた Pod を監視し、CRI を通じてコンテナランタイムを操作します。
- Pod の実行以外にも多くの責務があります。 Probe、Volume、リソース管理、Node の状態報告、GC、ログ管理などを担当します。
-
設定は
KubeletConfigurationが中心です。 feature gate が有効でも、ポリシーや猶予時間の指定、外部プラグインが必要な機能があります。 -
メトリクスは公開先を分けて確認します。
/metrics、/metrics/cadvisor、/metrics/resource、/metrics/probesでは取得できる情報が異なります。 - Pod の起動時間には複数の定義があります。 イメージ取得や init container の実行を含むかを確認して使うのが良いと思います。
第1章: kubelet の概要
kubelet の担当範囲と、Pod の更新を処理する仕組みを説明します。周辺コンポーネントとの分担を押さえると、障害時に調べる対象を絞りやすくなります。
kubelet は各 Node に配置され、API サーバーから取得した Pod の定義に基づいてコンテナランタイムと連携する。
(参考: Cluster Architecture)
1.1 kubelet の役割
公式ドキュメントは kubelet を、各 Node で動作し、Pod 内のコンテナが動いていることを保証するエージェントとして説明しています。
Ensures that Pods are running, including their containers.
(参考: Kubernetes Components - Node Components)
kubelet は各 Node に配置され、コンテナランタイムと連携して Pod を管理する。
(参考: Kubernetes Components)
kubelet は API サーバーから、自分の Node に割り当てられた Pod を取得します。実装では spec.nodeName を field selector にして List / Watch しています。コンテナを作成・停止する操作は、CRI (Container Runtime Interface) を通じて containerd や CRI-O などのコンテナランタイムに要求します。
(参考: apiserver.go#L34-L45、kuberuntime_manager.go#L1574-L1583)
| コンポーネント | 主な担当 |
|---|---|
| kube-scheduler | Pod を配置する Node を選ぶ |
| kube-controller-manager | ReplicaSet などの controller が必要な Pod を作成し、クラスターの状態を調整する |
| kubelet | 割り当てられた Pod を Node 上で実行し、状態を報告する |
| コンテナランタイム | CRI の要求を受けてコンテナや Pod sandbox を管理する |
| CNI プラグイン | ランタイムと連携して Pod のネットワークを設定する |
| CSI ドライバー | kubelet などからの要求を受けてストレージを操作する |
Pod の配置先の選択と Node 上での実行は別の処理です。スケジューリング済みでも、kubelet 側での admission、Volume の準備、イメージ取得などで起動できないことがあります。
(参考: Kubernetes Components、Container Runtime Interface、Network Plugins)
1.2 sync loop と Pod worker
kubelet の syncLoopIteration は、Pod 定義の変更、コンテナの状態変化、Probe の結果、定期的な同期・後始末などを受け取り、対象の Pod の処理につなげます。
| 同期のきっかけ | 処理の例 |
|---|---|
| Pod 定義の追加・変更・削除 | 起動、設定変更への対応、終了処理 |
| PLEG のイベント | コンテナの終了などを反映 |
| Probe の結果 | Ready 状態の変更、再起動の判断 |
| 定期的な同期 | 望ましい状態と実際の状態を再確認 |
| housekeeping | 不要になった Pod に関する後始末 |
(参考: kubelet.go#L2746-L2866)
Pod worker は、Pod ごとの同期と終了処理を管理します。通常の同期を行う SyncPod、コンテナを停止する SyncTerminatingPod、停止後のリソースを片付ける SyncTerminatedPod に処理が分かれています。
Pod の削除は、コンテナを停止しただけでは完了しません。 Volume などの後始末も進める必要があります。
(参考: pod_workers.go#L486-L510、kubelet.go)
第2章: kubelet の機能一覧
主な機能を役割ごとに分類しました。この分類は記事独自のもので、ソースコード上の manager の数や、全機能の総数を示すものではありません。
| 分類 | 機能 | 役割 | 利用条件・主な設定 |
|---|---|---|---|
| Pod の実行 | Pod の監視・同期 | Pod の定義と実行状態を照合する | 通常動作 |
| ローカル admission | Node 上で Pod を受け入れられるか判定する | リソース・各 manager の制約 | |
| コンテナ・sandbox 管理 | CRI を通じて作成・停止する | 対応するコンテナランタイム | |
| イメージ取得 | イメージの取得と認証情報を扱う |
imagePullPolicy、imagePullSecrets
|
|
| Probe | startup / liveness / readiness を実行する | Pod の各 Probe 設定 | |
| 終了処理・Lifecycle Hook | preStop などとコンテナの停止を扱う | Pod の Hook・終了猶予時間 | |
| Pod status の更新 | コンテナ状態・Pod Condition などを報告する | 通常動作 | |
| static Pod | ローカルのマニフェストから Pod を管理する |
staticPodPath など |
|
| リソース | cgroup / Node Allocatable | Pod のリソース制御とシステム用の予約を扱う |
kubeReserved、systemReserved など |
| CPU Manager | CPU の割り当てを管理する |
cpuManagerPolicy。デフォルト none
|
|
| Memory Manager | NUMA を考慮したメモリの割り当てを管理する |
memoryManagerPolicy。デフォルト None
|
|
| Topology Manager | CPU・メモリ・デバイスの NUMA 配置を調整する |
topologyManagerPolicy。デフォルト none
|
|
| Device Manager / DRA | デバイスの割り当てや利用前後の準備を扱う | Device Plugin / DRA ドライバー | |
| in-place resize | Pod の CPU・メモリの変更を反映する | resize の要求と適用条件 | |
| ストレージ・設定 | Volume Manager | Volume のマウント・アンマウントを管理する | Volume の種類、CSI ドライバーなど |
| ConfigMap / Secret / token | Pod が参照する設定やトークンを取得・更新する | Pod の参照・投影設定 | |
| Pod の DNS 設定 | DNS policy に応じてコンテナ用の DNS 設定を生成する |
clusterDNS、clusterDomain、Pod の dnsPolicy
|
|
| Node 管理 | Node status / Lease | Node の状態と heartbeat を報告する | 更新間隔・Lease の有効期間 |
| PLEG | ランタイム上の Pod・コンテナの状態変化を検知する | デフォルトは Generic PLEG | |
| node-pressure eviction | リソース不足時に Pod を終了して回収する |
evictionHard、evictionSoft など |
|
| graceful node shutdown | OS のシャットダウン時に Pod を終了する | 対応 OS と猶予時間の設定 | |
| メンテナンス・モニタリング | イメージ・コンテナ GC | 不要なイメージや終了済みコンテナを削除する | GC のしきい値など |
| コンテナログ管理 | ログファイルをローテーションする |
containerLogMaxSize など |
|
| API / 統計・メトリクス | logs・exec などの操作と観測情報を提供する | HTTPS API、認証・認可設定 |
(参考: kubelet.go、container_manager_linux.go#L257-L360、Kubelet Configuration)
2.1 デフォルトで動く機能と、追加設定が必要な機能
feature gate の有効・無効と、実際に機能を利用する条件は別です。 たとえば CPU Manager の static policy は明示的な設定が必要です。Probe は Pod に設定されたものだけが実行されます。
| 機能 | v1.37.1 での状態と利用条件 |
|---|---|
| Evented PLEG |
EventedPLEG は Alpha、デフォルト無効。対応するランタイムも必要 |
| graceful node shutdown |
GracefulNodeShutdown は Beta、デフォルト有効。ただし、猶予時間を設定しないデフォルト構成では Pod を順序立てて終了する処理は有効にならない |
| Swap |
NodeSwap は GA。ただし failSwapOn はデフォルト true。Swap を有効にした Node で利用するには追加設定が必要 |
| in-place resize |
InPlacePodVerticalScaling は GA、デフォルト有効。要求された変更が、その Pod・リソースの条件で実行可能である必要がある |
(参考: kube_features.go、defaults.go、nodeshutdown_manager_linux.go#L78-L100)
2.2 kubelet が担当しない処理
Deployment の replicas の維持、Pod の配置先の選択、Service のロードバランシング、ログの外部保存などには別のコンポーネントが関わります。kubelet の設定だけで、これらすべてを調整できるわけではありません。
| 処理 | 主な担当 |
|---|---|
| ReplicaSet の Pod 数の維持 | kube-controller-manager の ReplicaSet controller |
| Node 間での Pod の配置先の選択 | kube-scheduler |
| Service の転送ルールの管理 | kube-proxy、またはその代替となるネットワーク実装 |
| コンテナログの収集・検索・長期保存 | ログ収集エージェントと保存先 |
| Metrics API の提供 | Metrics Server など。kubelet は収集元の情報を提供する |
(参考: Kubernetes Components、Logging Architecture、Resource metrics pipeline)
第3章: 各機能の概要
一覧に挙げた機能について、処理の内容と周辺コンポーネントとの関係を説明します。設定の具体的な値は第4章、観測するメトリクスは第5章で整理します。
3.1 Pod の実行
Pod の監視・同期とローカル admission
API サーバーから届いた Pod を、Pod worker を通じて実行状態に反映します。新しい Pod を受け入れる際には、Node のリソースや各 manager の制約も確認します。Topology Manager の制約などによって、スケジューリング後に Pod が拒否される場合があります。
(参考: kubelet.go#L2883-L2962、topology_manager.go)
コンテナ・Pod sandbox とイメージ取得

kubelet は CRI を通じてコンテナランタイムに要求する。ランタイムは CNI プラグインによる Pod のネットワーク設定と、runc / crun などの OCI Runtime によるコンテナの実行を扱う。
SyncPod は、現在の状態から作成・停止が必要な sandbox とコンテナを判断します。Volume の準備を待つ処理は kubelet 側にあり、ランタイム側の同期では sandbox、init container、通常のコンテナなどを扱います。
イメージ取得では imagePullPolicy や認証情報に従い、ランタイムの ImageService に要求します。取得に失敗した場合はバックオフして再試行するため、ImagePullBackOff のときはレジストリへの接続や認証も確認する必要があります。
(参考: kubelet.go#L2230-L2245、kuberuntime_manager.go#L1574-L1583、image_manager.go)
Probe と Pod status
Probe Manager は、Probe が設定されているコンテナについて worker を作り、結果を保持します。
| Probe | 主な役割 | 失敗が続いた場合の動作 |
|---|---|---|
| startupProbe | 起動が完了したか確認する | コンテナを終了し、再起動ポリシーに従って再起動する |
| livenessProbe | コンテナが正常に動作しているか確認する | コンテナを終了し、再起動ポリシーに従って再起動する |
| readinessProbe | トラフィックを受けられる状態か確認する | Ready 状態を false にする。Probe の失敗だけでは再起動しない |
startupProbe を設定した場合、成功するまで liveness / readiness の Probe は開始されません。kubelet は結果を Pod status に反映します。Service の EndpointSlice などを更新する処理は、API サーバーに報告された状態を受けて別の controller が行います。
(参考: prober_manager.go、worker.go、kubelet.go#L2809-L2831)
Pod status には、コンテナの状態や再起動回数、Pod の Phase、Condition などが含まれます。Running であることと、Ready であることは別です。
(参考: kubelet_pods.go#L1910-L1945、status_manager.go)
static Pod
staticPodPath に置いたマニフェストなどを基に、kubelet が直接管理する Pod です。API サーバーには対応する mirror Pod を作成します。mirror Pod を API 経由で削除しても、元のマニフェストが残っていれば static Pod の削除にはなりません。
kubeadm が構成する Control Plane の kube-apiserver、kube-controller-manager、kube-scheduler などは、この仕組みを使います。
(参考: file.go、kubelet.go#L3552-L3586)
終了処理と Lifecycle Hook
通常の Pod の削除では、終了猶予時間を考慮してコンテナを停止します。preStop が設定されている場合は Hook を実行してから、残りの猶予時間を使ってランタイムに停止を要求します。postStart も kubelet が扱う Hook ですが、アプリケーションの処理開始より必ず先に完了するものではありません。
(参考: kuberuntime_container.go、handlers.go)
3.2 リソース管理
cgroup と Node Allocatable
Linux では cgroup を使い、Pod・コンテナの CPU やメモリなどのリソース制御を行います。Node Allocatable は、Node 全体の容量からシステム用の予約などを考慮した、Pod に使えるリソースです。
kubeReserved と systemReserved は、それぞれ Kubernetes 関連プロセスと OS 関連プロセスに必要なリソースの予約を表します。予約したリソースを対応する cgroup に強制する設定は別にあるため、予約値の指定とプロセスへの制限を区別する必要があります。
(参考: node_container_manager_linux.go、container_manager_linux.go)
CPU Manager / Memory Manager / Topology Manager
| manager | 主な役割 | デフォルトの policy |
|---|---|---|
| CPU Manager |
static policy などにより、条件を満たすコンテナに専用 CPU を割り当てる |
none |
| Memory Manager |
Static policy などにより、NUMA ノードを考慮してメモリを割り当てる |
None |
| Topology Manager | CPU・メモリ・デバイスの割り当て候補をまとめ、NUMA 配置の条件を判定する | none |
これらの policy が none / None でも、通常の CPU・メモリの requests / limits に基づくリソース管理が無効になるわけではありません。専用 CPU や NUMA 配置の調整を使う場合に、追加の policy を設定します。
(参考: cpu_manager.go、memory_manager.go、topology_manager.go、defaults.go#L171-L185)
Device Manager / Dynamic Resource Allocation
Device Manager は Device Plugin の登録やデバイスの割り当てを扱います。GPU などを利用する場合、デバイス固有のプラグインは別途必要です。
DRA では ResourceClaim などに基づき、Node 上のドライバーに利用前の準備・利用後の解除を要求します。クラスター側での割り当て判断と、Node 上での準備は分担されています。
(参考: manager.go (Device Manager)、manager.go (DRA))
in-place resize
Pod の CPU・メモリの変更を、同じ Pod のまま反映する処理です。kubelet は Node 上で実行可能かを判定し、リソースの割り当てやランタイムへの更新を進めます。リソース不足などで延期される場合があり、resize policy によってはコンテナの再起動が必要です。
(参考: allocation_manager.go、kuberuntime_manager.go)
3.3 ストレージ・設定の反映
Volume Manager
Pod が必要とする Volume と、実際にマウントされている Volume を照合し、マウント・アンマウントなどを進めます。CSI Volume では、Node 側の処理を CSI ドライバーに要求します。
PV / PVC のバインドや、一般的な構成での attach / detach の制御には kube-controller-manager 側も関わります。Volume 関連の問題は、Node 側のマウント処理とクラスター側の処理を分けて確認するのが良いと思います。
(参考: volume_manager.go、reconciler.go)
ConfigMap / Secret / ServiceAccount token
Pod が参照する ConfigMap と Secret を取得・キャッシュします。変更検知のデフォルトは Watch です。Volume として投影した値の反映は非同期であり、環境変数に渡した値は既存のコンテナへ自動では反映されません。
ServiceAccount token の投影では、TokenRequest API を使ってトークンを取得し、有効期限などに応じて更新します。kubelet 自身がトークンに署名するわけではありません。
(参考: configmap_manager.go、secret_manager.go、token_manager.go#L96-L130)
補足: ConfigMap / Secret の変更がファイルに反映されるまで
通常の ConfigMap / Secret Volume では、変更の検知とマウント済みファイルの更新は別の処理です。デフォルトの configMapAndSecretChangeDetectionStrategy: Watch では、次の順序で反映されます。
- API サーバーからの Watch イベントで、kubelet 内のキャッシュを更新する
- Pod の定期同期でキャッシュを参照し、Volume 内のファイルを更新する
Watch イベントを受けた瞬間に、Pod 内のファイルが更新されるわけではありません。 定期同期の間隔は syncFrequency (デフォルト 1m) が基準です。v1.37.1 の Pod worker は 0〜50% のジッターを加えて次の同期を予約するため、通常の定期同期の間隔は約 60〜90 秒になります。変更からの待ち時間は、その時点から次の同期までの残り時間と Watch の伝播時間、Volume の更新処理などによって変わります。60〜90 秒が反映時間の保証や、変更後に必ず待つ時間という意味ではありません。
syncFrequency を短くすると反映待ちを短縮できますが、ConfigMap / Secret 以外も含めた Pod の同期処理が増えます。ファイルが更新された後にアプリケーションが設定を再読み込みするかも、別に確認する必要があります。また、環境変数として渡した値や、subPath でマウントしたファイルは、この仕組みでは自動更新されません。
(参考: ConfigMaps - Mounted ConfigMaps are updated automatically、Secrets - Using Secrets as files from a Pod、pod_workers.go#L1524-L1531)
大規模環境では、変更しない設定を immutable にすることも負荷軽減に有効です。 ConfigMap / Secret に immutable: true を指定すると、kubelet はそのオブジェクトの変更監視を停止でき、API サーバーの Watch の負荷を減らせます。特に、多数の異なる ConfigMap / Secret を Pod が参照する環境で検討する価値があります。ただし、Pod 自体の定期同期がなくなるわけではありません。
apiVersion: v1
kind: ConfigMap
metadata:
name: app-config-v1
immutable: true
data:
log-level: info
immutable にするとデータの変更や immutable: false への変更はできません。設定を更新する場合は、たとえば app-config-v2 のように別名で新しいオブジェクトを作り、Deployment などの Pod template の参照先を変更して Pod を入れ替える運用が良いと思います。Secret のローテーションでも同様に、参照先の切り替えと Pod の更新を合わせて設計します。
(参考: ConfigMaps - Immutable ConfigMaps、Secrets - Immutable Secrets、watch_based_manager.go)
Pod の DNS 設定
Pod の dnsPolicy や dnsConfig、kubelet の clusterDNS / clusterDomain などを基に、コンテナに渡す DNS 設定を生成します。kubelet は DNS サーバーそのものではなく、クラスター内の DNS 問い合わせへの応答は CoreDNS などが担当します。
(参考: dns.go)
3.4 Node の状態管理
Node status と Lease
Node status では、Capacity / Allocatable、Ready などの Condition、アドレス、ランタイム情報などを報告します。heartbeat には Node status の更新に加えて、kube-node-lease Namespace の Lease の更新も使います。
Lease の有効期間のデフォルトは 40 秒で、通常の更新間隔はその 1/4 の 10 秒です。nodeStatusUpdateFrequency のデフォルトも 10 秒ですが、これは状態を計算する間隔です。変化がない場合の報告間隔は nodeStatusReportFrequency によるため、Node status 全体を常に 10 秒ごとに送信する意味ではありません。
(参考: kubelet.go#L1155-L1168、kubelet_node_status.go、defaults.go#L137-L156)
PLEG
PLEG (Pod Lifecycle Event Generator) は、ランタイム上の Pod・コンテナの状態変化を検知し、同期処理につなげます。デフォルトの Generic PLEG は、ランタイムの状態を定期的に確認します。
PLEG が正常に状態を確認できなくなると、kubelet の runtime health の判定に影響します。Node が NotReady になった場合は、kubelet とランタイムのログに加えて、PLEG の確認処理の所要時間や最終確認時刻も調べるのが良いと思います。
(参考: generic.go#L235-L247、kubelet.go#L3321-L3365)
node-pressure eviction
メモリ、ディスク容量、inode、PID などの不足を検知し、しきい値に応じて回収処理や Pod の終了を行います。ディスク不足では、不要なコンテナやイメージの回収で解消できるかも確認します。
これは kubelet が Node の資源を守るために行う処理です。API サーバーの Eviction API を使う退避とは異なり、PodDisruptionBudget による保護の対象にはなりません。
(参考: eviction_manager.go、Node-pressure Eviction)
graceful node shutdown
Linux では systemd のシャットダウン通知と連携して、OS が終了する前に Pod を終了する時間を確保します。通常の Pod と critical Pod に配分する時間などを設定できます。
feature gate がデフォルトで有効でも、shutdownGracePeriod などの猶予時間の設定が必要です。また、突然の電源断のように OS の終了通知を受け取れない状況では、この処理を実行できません。
(参考: nodeshutdown_manager_linux.go)
3.5 メンテナンス・モニタリング
イメージ・コンテナ GC とログ管理
Image GC は、イメージ用ファイルシステムの使用率が高くなったときなどに、未使用のイメージを削除します。デフォルトでは使用率 85% が回収の開始しきい値、80% が回収後の目標です。使用中のイメージなどは削除できないため、必ず目標まで空くわけではありません。
Container GC は不要な終了済みコンテナを回収します。これは API サーバー上の終了済み Pod オブジェクトを削除する Pod GC controller とは別の処理です。
(参考: image_gc_manager.go#L349-L418、kuberuntime_gc.go)
コンテナの標準出力・標準エラーのログについては、ランタイムが書き込むファイルを kubelet がローテーションします。デフォルトは 1 ファイル 10Mi、保持数 5 です。監視と処理は非同期のため、ファイルサイズが一時的に設定値を超えることがあります。ログの収集・長期保存は別途用意します。
(参考: container_log_manager.go)
API・統計情報の提供
kubelet は HTTPS API を持ち、ログ取得、exec、attach、port-forward、統計・メトリクスなどの要求を扱います。デフォルトの HTTPS ポートは 10250 です。通常、利用者は kubectl と API サーバーを通じて操作します。
統計情報には JSON 形式の /stats/summary と、Prometheus 形式の各 /metrics エンドポイントがあります。後者の使い分けは第5章で整理します。
(参考: server.go、stats (server))
第4章: 設定一覧
機能の動作に関わる主な設定を抜粋します。すべてのノードに同じ値を適用する前に、ランタイム、OS、ハードウェアやワークロードの条件も確認するのが良いと思います。
4.1 設定ファイルと実効設定
設定ファイルは --config で読み込みます。以下は構文の例です。設定変更は、利用している Node の構成管理の仕組みに従って反映します。
apiVersion: kubelet.config.k8s.io/v1beta1
kind: KubeletConfiguration
maxPods: 110
serializeImagePulls: true
imageGCHighThresholdPercent: 85
imageGCLowThresholdPercent: 80
containerLogMaxSize: 10Mi
containerLogMaxFiles: 5
# 起動時に設定ファイルを指定する例
kubelet --config=/var/lib/kubelet/config.yaml
設定ファイルと同じ項目を CLI でも指定した場合、CLI の値が優先されます。--config-dir による追加設定もあるため、起動引数と読み込むファイルを合わせて確認します。
(参考: Set Kubelet Parameters Via A Configuration File、options.go)
起動中の設定は、/configz が有効でアクセス権限がある環境では、次のように確認できます。これは確認用コマンド例です。
NODE='worker-node-name' # 確認対象の Node 名に置き換える
kubectl get --raw "/api/v1/nodes/${NODE}/proxy/configz"
以下の表は 設定ファイルのデフォルト値 です。設定ファイルを読み込まず CLI の互換用デフォルトで起動する場合は、認証・認可や read-only port などに異なる値があります。kubeadm などが設定を書き込む場合もあるため、実環境の値は /configz と起動引数で確認します。
(参考: defaults.go、options.go#L212-L225、server.go#L658-L659)
4.2 Pod の実行・API 通信
| 設定 | デフォルト | 内容・調整の観点 |
|---|---|---|
syncFrequency |
1m |
Pod を定期的に同期する最大間隔。Pod の変更はイベントでも処理するため、新規 Pod が毎回 1 分待つ意味ではない |
fileCheckFrequency |
20s |
static Pod のファイルを確認する間隔 |
maxPods |
110 |
Node で実行できる Pod 数の上限 |
serializeImagePulls |
true |
イメージ取得を直列化。maxParallelImagePulls の指定によってデフォルトが変わる |
maxParallelImagePulls |
未指定 | 並列取得の上限。2 以上を指定し serializeImagePulls を省略すると、直列化は false になる |
registryPullQPS / registryBurst
|
5 / 10
|
イメージ取得要求のレート制限。転送帯域の上限ではない |
runtimeRequestTimeout |
2m |
ランタイム要求のタイムアウト。長時間の処理など、一律に適用されない要求もある |
kubeAPIQPS / kubeAPIBurst
|
50 / 100
|
API サーバーへの通常の通信のレート制限。Event と Node heartbeat は別に扱う |
eventRecordQPS / eventBurst
|
50 / 100
|
Event の送信に使うレート制限 |
(参考: defaults.go、types.go (KubeletConfiguration)、options.go#L487-L488)
イメージ取得の並列数を増やすと、Node のディスク・ネットワークやレジストリの負荷が増えます。起動が遅い場合は、取得要求の待ち時間と実際の転送・展開にかかる時間を分けて考えるのが良いと思います。
4.3 リソース・ストレージ
| 設定 | デフォルト | 内容 |
|---|---|---|
cpuManagerPolicy |
none |
CPU の割り当て policy |
memoryManagerPolicy |
None |
メモリの割り当て policy |
topologyManagerPolicy / topologyManagerScope
|
none / container
|
NUMA 配置の policy と適用単位 |
kubeReserved / systemReserved
|
未指定 | Kubernetes・OS 用のリソース予約 |
enforceNodeAllocatable |
[pods] |
Node Allocatable の強制対象 |
podPidsLimit |
-1 |
Pod の PID 上限。デフォルトは Node Allocatable の PID 制約を利用 |
failSwapOn |
true |
Swap が有効な場合、kubelet の起動を失敗させる |
configMapAndSecretChangeDetectionStrategy |
Watch |
ConfigMap / Secret の変更検知方法 |
clusterDNS / clusterDomain
|
未指定 / 空文字列 | クラスターの DNS サーバー IP とドメイン。実環境では kubeadm などが値を設定する |
volumeStatsAggPeriod |
1m |
Volume の使用量などの統計を収集する間隔 |
(参考: defaults.go、types.go)
4.4 Node の状態・GC・ログ
| 設定 | デフォルト | 内容 |
|---|---|---|
nodeStatusUpdateFrequency |
10s |
Node の状態を計算する間隔 |
nodeStatusReportFrequency |
5m |
状態に変化がない場合の報告間隔。nodeStatusUpdateFrequency を明示した場合のデフォルトはその値 |
nodeLeaseDurationSeconds |
40 |
Node の Lease の有効期間。通常の更新間隔はその 1/4 |
shutdownGracePeriod / shutdownGracePeriodCriticalPods
|
0s / 0s
|
Node shutdown 時の終了猶予。デフォルトではこの時間配分による処理は無効 |
imageGCHighThresholdPercent / imageGCLowThresholdPercent
|
85 / 80
|
Image GC の開始しきい値・回収後の目標使用率 |
imageMinimumGCAge |
2m |
GC の対象とするイメージの最小経過時間 |
containerLogMaxSize / containerLogMaxFiles
|
10Mi / 5
|
ローテーションするログのサイズ・保持数 |
containerLogMaxWorkers / containerLogMonitorInterval
|
1 / 10s
|
ログのローテーションの並列数・監視間隔 |
evictionPressureTransitionPeriod |
5m |
Pressure Condition の解除時に状態の揺れを抑える時間。Pod 退避を必ず 5 分待つ意味ではない |
mergeDefaultEvictionSettings |
false |
カスタムの eviction 設定へデフォルトの値をマージするか |
Linux の evictionHard のデフォルトは次の通りです。
| シグナル | しきい値 |
|---|---|
memory.available |
100Mi 未満 |
nodefs.available |
10% 未満 |
nodefs.inodesFree |
5% 未満 |
imagefs.available |
15% 未満 |
imagefs.inodesFree |
5% 未満 |
evictionHard の一部を変更した場合、mergeDefaultEvictionSettings: false では、指定しなかった項目にデフォルトのしきい値が自動で補われません。メモリの値だけ変更して、意図せずディスクのしきい値を外さないように確認するのが良いと思います。
(参考: defaults.go、defaults_linux.go#L20-L28、types.go)
4.5 HTTPS API と認証・認可
| 設定 | デフォルト | 内容 |
|---|---|---|
address / port
|
0.0.0.0 / 10250
|
HTTPS API の待ち受け |
readOnlyPort |
0 |
read-only HTTP ポート。設定ファイルのデフォルトでは無効 |
authentication.anonymous.enabled |
false |
匿名認証の有効・無効 |
authentication.webhook.enabled |
true |
TokenReview による認証 |
authorization.mode |
Webhook |
SubjectAccessReview による認可 |
healthzBindAddress / healthzPort
|
127.0.0.1 / 10248
|
ヘルスチェック用の待ち受け |
(参考: defaults.go#L74-L135、Kubelet Configuration)
第5章: メトリクス一覧
kubelet 自体の処理と、Pod・コンテナのリソース使用量は、異なるメトリクスとして公開されます。主な公開先と、問題の切り分けに使う指標を整理します。
5.1 公開先
| エンドポイント | 主な情報 |
|---|---|
/metrics |
Pod の同期・起動、ランタイム要求、PLEG、eviction、Volume 統計など |
/metrics/cadvisor |
コンテナの CPU・メモリ・ファイルシステム・ネットワークなどの統計。収集実装は feature gate などの条件で変わる |
/metrics/resource |
Node・Pod・コンテナの CPU / メモリなど、リソース監視用の統計 |
/metrics/probes |
startup / liveness / readiness Probe の結果・応答時間 |
/stats/summary は JSON の統計 API であり、Prometheus 形式のメトリクスではありません。
(参考: server.go#L510-L565、resource_metrics.go)
API サーバー経由で確認するコマンド例です。Node の proxy API へのアクセス権限が必要です。出力される系列は、その Node の機能・実行状態によって異なります。
NODE='worker-node-name' # 確認対象の Node 名に置き換える
kubectl get --raw "/api/v1/nodes/${NODE}/proxy/metrics"
kubectl get --raw "/api/v1/nodes/${NODE}/proxy/metrics/cadvisor"
kubectl get --raw "/api/v1/nodes/${NODE}/proxy/metrics/resource"
kubectl get --raw "/api/v1/nodes/${NODE}/proxy/metrics/probes"
5.2 kubelet 内部の処理
以下は /metrics の主な指標です。Histogram は観測値の分布、Counter は累積回数、Gauge はその時点の値を示します。
| メトリクス | 型 | 見ること |
|---|---|---|
kubelet_pod_worker_duration_seconds |
Histogram | Pod の同期処理時間。operation_type 別 |
kubelet_pod_start_duration_seconds |
Histogram | kubelet が最初に Pod を認識してから、起動するまでの時間 |
kubelet_pod_start_total_duration_seconds |
Histogram | Pod の作成時刻から起動の観測まで。イメージ取得・init container の実行時間を含む |
kubelet_pod_start_sli_duration_seconds |
Histogram | Pod の起動時間。イメージ取得・init container の実行時間を除く |
kubelet_runtime_operations_total |
Counter | ランタイムへの要求数。operation_type 別 |
kubelet_runtime_operations_duration_seconds |
Histogram | ランタイム要求の所要時間 |
kubelet_runtime_operations_errors_total |
Counter | ランタイム要求のエラー数 |
kubelet_pleg_relist_duration_seconds |
Histogram | PLEG の状態確認にかかる時間 |
kubelet_pleg_relist_interval_seconds |
Histogram | PLEG の状態確認の間隔 |
kubelet_pleg_last_seen_seconds |
Gauge | PLEG の最終確認時刻。経過秒数ではなく Unix timestamp |
kubelet_running_pods / kubelet_running_containers
|
Gauge | 実行中の Pod・コンテナ数 |
kubelet_evictions |
Counter | kubelet による Pod の eviction 回数。eviction_signal 別 |
kubelet_image_pull_duration_seconds |
Histogram | イメージの取得時間。取得処理のキューで待つ時間を含む |
kubelet_volume_stats_available_bytes / kubelet_volume_stats_used_bytes
|
Gauge | PVC の利用可能容量・使用量。Volume が統計の取得に対応している場合 |
(参考: metrics.go#L294-L550、metrics.go#L703-L719、metrics.go#L1121-L1130、volume_stats.go)
Pod の起動メトリクスは、アプリケーションが Ready になるまでの時間と同じではありません。 とくに pod_start_sli_duration_seconds と pod_start_total_duration_seconds は、イメージ取得と init container の時間を含むかが異なります。測定の開始・終了条件を揃えて比較する必要があります。
v1.37.1 の起動時間トラッカーは、各コンテナが起動した状態を status の Watch で観測した時点で記録します。また、SLI の対象からは、利用する Volume の種類で stateful と判定される Pod などが除外されます。すべての Pod が同じ母集団で集計されるわけではありません。
(参考: pod_startup_latency_tracker.go)
5.3 Probe とリソース使用量
| 公開先 | メトリクス | 型 | 見ること |
|---|---|---|---|
/metrics/probes |
prober_probe_total |
Counter | Probe の実行結果。probe_type、result、Pod・コンテナなどで区別 |
/metrics/probes |
prober_probe_duration_seconds |
Histogram | Probe の応答時間。Failure の試行は記録されず、全試行の遅延分布ではない |
/metrics/resource |
node_cpu_usage_seconds_total |
Counter | Node の CPU 使用時間 |
/metrics/resource |
node_memory_working_set_bytes |
Gauge | Node のメモリ working set |
/metrics/resource |
container_cpu_usage_seconds_total |
Counter | コンテナの CPU 使用時間 |
/metrics/resource |
container_memory_working_set_bytes |
Gauge | コンテナのメモリ working set |
/metrics/cadvisor |
container_network_receive_bytes_total / container_network_transmit_bytes_total
|
Counter | コンテナのネットワーク受信・送信バイト数 |
(参考: prober_manager.go#L40-L70、worker.go、resource_metrics.go#L29-L93、Kubernetes Metrics Reference)
CPU 使用時間の Counter は、rate() を使うと単位時間あたりの使用量になります。たとえば 1 秒あたり 1 CPU 秒なら、平均で 1 コアを使っていることに相当します。メモリ working set は、そのままコンテナの memory limit の使用率や OOM の判定値を示すものではありません。
同名の CPU・メモリ指標が複数の公開先にあるため、Prometheus 側で両方を収集している場合は、対象の scrape job を絞って二重集計を避けます。
5.4 問題とメトリクスの対応
| 症状 | 確認するメトリクス | 合わせて確認すること |
|---|---|---|
| Pod の起動が遅い |
kubelet_pod_start_total_duration_seconds、kubelet_image_pull_duration_seconds
|
Pod の Event、init container、Volume の準備 |
| 多くの Pod で操作が遅い |
kubelet_pod_worker_duration_seconds、kubelet_runtime_operations_duration_seconds
|
Node の CPU・ディスク・ランタイムの状態 |
| Node が NotReady になる |
kubelet_pleg_last_seen_seconds、PLEG の所要時間・間隔 |
kubelet のログ、Node Condition、heartbeat、ランタイムへの接続 |
| Probe が失敗する |
prober_probe_total、prober_probe_duration_seconds
|
timeout、アプリケーションの状態、Node の負荷 |
| Pod が Evicted になる |
kubelet_evictions、Volume・Node の使用量 |
eviction signal、Node Condition、しきい値 |
ランタイム要求のエラーを、操作ごとの毎秒の増加量で確認する例です。
sum by (instance, operation_type) (
rate(kubelet_runtime_operations_errors_total[5m])
)
PLEG が最後に状態を確認してからの経過秒数は、次のように計算できます。
time() - kubelet_pleg_last_seen_seconds
メトリクスには Alpha のものも含まれます。バージョン、feature gate、OS、統計を取得するランタイム・Volume の対応状況によって、系列の有無や利用条件が変わります。定義が存在することと、すべての Node でその系列が出力されることは別です。
おわりに
kubelet の機能を並べると、Pod の起動と終了の間にも、Probe、リソース管理、状態報告、不要なデータの回収といった処理が動いていることが分かります。トラブル時には、まず「どの処理で止まっているか」を絞り、対応する設定・ログ・メトリクスを合わせて確認するのが良いと思います。
参考
参考リンク
本文で登場する順に、主な公式ドキュメントを並べています。