hana_shinのLinux技術ブログ

Linuxの技術情報を掲載しています。特にネットワークをメインに掲載していきます。

KubernetesのNamespaceを理解する~ Leaseオブジェクトはどのように更新されるのか



1 Namespaceとは

Namespaceは、単一のクラスタ内を論理的に分割する仕組みです。チームや環境(開発・本番など)ごとにリソースを分けて管理できるため、複数のチームでクラスタを共有する際に役立ちます。たとえば、チームAとチームBが同じクラスタを使用している場合、チームAは team-a、チームBは team-b といったNamespaceをそれぞれ利用することで、お互いのリソース名が衝突することなく独立して開発を進めることができます。なお、PodやServiceなどのリソースはNamespaceごとに分離されますが、Nodeやストレージ(PersistentVolume)などはクラスタ全体で共有されるリソースです。

2 検証環境

2.1 ネットワーク構成

検証環境は3台の仮想マシンでKubernetesクラスタを構成しています。

+--- control ---+    +--- worker1 ---+   +--- worker2 ---+
|               |    |               |   |               |
|AlmaLinux 10.2 |    |AlmaLinux 10.2 |   |AlmaLinux 10.2 |
|               |    |               |   |               |
+-------+-------+    +-------+-------+   +-------+-------+
        |.19                 |.20                |.22
        |                    |                   |
        |                    |                   |
        |   192.168.1.0/24   |                   |
+--------------------------------------------------------+
|                           KVM                          |
+--------------------------------------------------------+

それぞれの役割は以下のとおりです。
1台をコントロールノード、2台をワーカーノードとして使用します。

ホスト名 名称 役割
control コントロールノード クラスタ(control、worker1、worker2)の状態を管理し、Pod をどのノードで実行するかを決定するノード
worker1 ワーカーノード Pod を実行するノード
worker2 ワーカーノード Pod を実行するノード

2.2 ソフトウェアのバージョン

各ノードのAlmaLinuxバージョンは以下のとおりです。

[root@control ~]# cat /etc/redhat-release
AlmaLinux release 10.2 (Lavender Lion)

各ノードのカーネルバージョンは以下のとおりです。

[root@control ~]# uname -r
6.12.0-211.7.3.el10_2.x86_64

Kubernetesのバージョンは以下のとおりです。

[root@control ~]# kubectl version
Client Version: v1.35.3
Kustomize Version: v5.7.1
Server Version: v1.35.3

2.3 ノードのリソース

各ノードには4GBのメモリを割り当てています。

[root@control ~]#  free -h
               total        used        free      shared  buff/cache   available
Mem:           3.6Gi       1.3Gi       1.0Gi       5.8Mi       1.5Gi       2.3Gi
Swap:             0B          0B          0B

各ノードは 4コアのCPU(4 vCPU) を搭載しています。

[root@control ~]# lscpu -xe
CPU NODE SOCKET CORE L1d:L1i:L2:L3 ONLINE
  0    0      0    0 0:0:0:0          yes
  1    0      1    1 1:1:1:1          yes
  2    0      2    2 2:2:2:2          yes
  3    0      3    3 3:3:3:3          yes

lscpuコマンドの詳しい使い方は、以下のページをご覧ください。
hana-shin.hatenablog.com

3 Namespaceの使い方

3.1 Namespace一覧の確認方法

クラスター内のNamespace一覧を表示します。

[root@control ~]# kubectl get namespaces
NAME              STATUS   AGE
default           Active   10d
kube-node-lease   Active   10d
kube-public       Active   10d
kube-system       Active   10d
Namespace 説明
default Namespaceを指定しなかった場合に使われる、デフォルトのNamespace
kube-system Kubernetesシステムが作成するオブジェクトのためのNamespace
kube-public 未認証のクライアントも含め、全員が読み取り可能なNamespace。クラスター全体に公開したい情報を置く用途を想定しているが、公開は運用上の慣習であり必須ではない
kube-node-lease 各ノードに対応するLeaseオブジェクトを格納するNamespace。各ノードのkubeletがLeaseオブジェクトを定期的に更新し、コントロールプレーンはその更新状況を監視してノードの生存状態を確認する

kubernetes.io

3.2 Namespaceの作成・削除方法

team-aという名前のNamespaceを作成します。

[root@control ~]# kubectl create namespace team-a
namespace/team-a created

再度、クラスタに存在するNamespace一覧を表示します。team-a というNamespaceが新しく作成されたことが確認できます。

[root@control ~]# kubectl get namespaces
NAME              STATUS   AGE
default           Active   10d
kube-node-lease   Active   10d
kube-public       Active   10d
kube-system       Active   10d
team-a            Active   9s

team-aという名前のNamespaceを削除します。

[root@control ~]# kubectl delete namespaces team-a
namespace "team-a" deleted

再度、クラスタに存在するNamespaceの一覧を表示します。team-a というNamespaceが削除されたことが確認できます。

[root@control ~]# kubectl get namespaces
NAME              STATUS   AGE
default           Active   10d
kube-node-lease   Active   10d
kube-public       Active   10d
kube-system       Active   10d

3.3 指定したNamespaceにリソースを作成する方法

(1) リソースの作成
ここでは、team-a と team-b というNamespaceを作成し、それぞれでPodを起動してみます。

team-aという名前のNamespaceを作成します。

[root@control ~]# kubectl create namespace team-a
namespace/team-a created

team-bという名前のNamespaceを作成します。

[root@control ~]# kubectl create namespace team-b
namespace/team-b created

Namespace一覧を確認します。

[root@control ~]# kubectl get namespaces
NAME              STATUS   AGE
default           Active   11d
kube-node-lease   Active   11d
kube-public       Active   11d
kube-system       Active   11d
team-a            Active   87s
team-b            Active   85s

default のnamespaceでNginxのPodを起動します。

[root@control ~]# kubectl run nginx-default --image=nginx
pod/nginx-default created

team-a のnamespaceでNginxのPodを起動します。

[root@control ~]# kubectl run nginx-a --image=nginx --namespace=team-a
pod/nginx-a created

team-b のnamespaceでNginxのPodを起動します。

[root@control ~]# kubectl run nginx-b --image=nginx --namespace=team-b
pod/nginx-b created

defaultのnamespaceでNginxのPodが動作していることが確認できます。

[root@control ~]# kubectl get pods
NAME            READY   STATUS    RESTARTS   AGE
nginx-default   1/1     Running   0          65s

team-aという名前のnamespaceでNginxのPodが動作していることが確認できます。

[root@control ~]# kubectl get pods --namespace=team-a
NAME      READY   STATUS    RESTARTS   AGE
nginx-a   1/1     Running   0          45s

team-bという名前のnamespaceでNginxのPodが動作していることが確認できます。

[root@control ~]# kubectl get pods --namespace=team-b
NAME      READY   STATUS    RESTARTS   AGE
nginx-b   1/1     Running   0          37s

-A オプションを使用すると、すべてのNamespaceに存在するリソースを確認することができます。以下の例では、NginxのPodが default、team-a、team-b の各Namespaceで動作していることが確認できます。

[root@control ~]# kubectl get pods -A
NAMESPACE     NAME                                     READY   STATUS    RESTARTS       AGE
default       nginx-default                            1/1     Running   0              3m31s
kube-system   calico-kube-controllers-9dff488b-sxpdb   1/1     Running   13 (21m ago)   23d
kube-system   calico-node-7m6ph                        1/1     Running   13 (21m ago)   23d
kube-system   calico-node-vcmh5                        1/1     Running   13 (21m ago)   23d
kube-system   calico-node-w7ldj                        1/1     Running   13 (21m ago)   23d
kube-system   coredns-66869746d6-45g95                 1/1     Running   2 (21m ago)    2d23h
kube-system   coredns-66869746d6-zk5p6                 1/1     Running   2 (21m ago)    2d23h
kube-system   etcd-control                             1/1     Running   26 (21m ago)   23d
kube-system   kube-apiserver-control                   1/1     Running   25 (21m ago)   23d
kube-system   kube-controller-manager-control          1/1     Running   15 (21m ago)   23d
kube-system   kube-proxy-426t6                         1/1     Running   13 (21m ago)   23d
kube-system   kube-proxy-gr68g                         1/1     Running   13 (21m ago)   23d
kube-system   kube-proxy-krgq6                         1/1     Running   13 (21m ago)   23d
kube-system   kube-scheduler-control                   1/1     Running   15 (21m ago)   23d
team-a        nginx-a                                  1/1     Running   0              91s
team-b        nginx-b                                  1/1     Running   0              74s


(2) リソースの削除

Namespace team-a に存在するPodを削除します。

[root@control ~]# kubectl delete pod nginx-a -n team-a
pod "nginx-a" deleted from team-a namespace

Namespace team-b に存在するPodを削除します。

[root@control ~]# kubectl delete pod nginx-b -n team-b
pod "nginx-b" deleted from team-b namespace

default Namespaceに存在するPodを削除します。Namespaceを指定しない場合は、default が対象となります。

[root@control ~]# kubectl delete pod nginx
pod "nginx" deleted from default namespace

すべてのNamespaceのPod一覧を確認し、対象のPodが削除されていることを確認します。

[root@control ~]# kubectl get pod -A
NAMESPACE     NAME                                     READY   STATUS    RESTARTS       AGE
kube-system   calico-kube-controllers-9dff488b-sxpdb   1/1     Running   13 (50m ago)   23d
kube-system   calico-node-7m6ph                        1/1     Running   13 (49m ago)   23d
kube-system   calico-node-vcmh5                        1/1     Running   13 (50m ago)   23d
kube-system   calico-node-w7ldj                        1/1     Running   13 (49m ago)   23d
kube-system   coredns-66869746d6-45g95                 1/1     Running   2 (50m ago)    3d
kube-system   coredns-66869746d6-zk5p6                 1/1     Running   2 (49m ago)    3d
kube-system   etcd-control                             1/1     Running   26 (50m ago)   23d
kube-system   kube-apiserver-control                   1/1     Running   25 (50m ago)   23d
kube-system   kube-controller-manager-control          1/1     Running   15 (50m ago)   23d
kube-system   kube-proxy-426t6                         1/1     Running   13 (49m ago)   23d
kube-system   kube-proxy-gr68g                         1/1     Running   13 (50m ago)   23d
kube-system   kube-proxy-krgq6                         1/1     Running   13 (49m ago)   23d
kube-system   kube-scheduler-control                   1/1     Running   15 (50m ago)   23d

3.4 デフォルトNamespaceの確認・変更

現在のデフォルトNamespaceを確認します。この時点ではNamespaceが設定されていないため、何も表示されません(デフォルトでは default Namespaceが使用されます)。

[root@control ~]# kubectl config view --minify | grep namespace:
[root@control ~]#

デフォルトのNamespaceを team-a に変更します。

[root@control ~]# kubectl config set-context --current --namespace=team-a
Context "kubernetes-admin@kubernetes" modified.

再度、現在のデフォルトNamespaceを確認します。team-a に変更されていることが確認できます。

[root@control ~]# kubectl config view --minify | grep namespace:
    namespace: team-a

続いて、デフォルトのNamespaceを team-b に変更します。

[root@control ~]# kubectl config set-context --current --namespace=team-b
Context "kubernetes-admin@kubernetes" modified.

現在のデフォルトNamespaceを確認すると、team-b に変更されていることが確認できます。

[root@control ~]# kubectl config view --minify|grep namespace
    namespace: team-b

この状態で kubectl get pods を実行すると、デフォルトのNamespaceである team-b のPodが表示されます。

[root@control ~]# kubectl get pods
NAME      READY   STATUS    RESTARTS   AGE
nginx-b   1/1     Running   0          11m

--namespace オプションを指定することで、他のNamespaceのPodを確認することもできます。まず、default NamespaceのPodを確認します。

[root@control ~]# kubectl get pods --namespace=default
NAME            READY   STATUS    RESTARTS   AGE
nginx-default   1/1     Running   0          12m

続いて、team-a NamespaceのPodを確認します。

[root@control ~]# kubectl get pods --namespace=team-a
NAME      READY   STATUS    RESTARTS   AGE
nginx-a   1/1     Running   0          12m

4 kube-node-leaseについて

kube-node-lease Namespaceの使用目的は、各ノードに対応するLeaseオブジェクトを格納することです。Leaseオブジェクトは、各ノードのkubeletによって定期的に更新され、ノードの生存監視(ハートビート)に使用されます。各ノードのkubeletは、自身に対応するLeaseオブジェクトが存在しない場合、Leaseオブジェクトを作成します。作成要求はkube-apiserver経由で送信され、Leaseオブジェクトはetcdに保存されます。その後、kubeletは一定間隔(デフォルトでは約10秒ごと)で、kube-apiserver経由でLeaseオブジェクトのspec.renewTimeを更新します。更新されたLeaseオブジェクトは、kube-apiserverによってetcdに保存されます。

万一、kubeletの停止やノード障害、ネットワーク障害などによりspec.renewTimeが更新されなくなると、コントロールプレーンはLeaseオブジェクトの更新が一定時間行われていないことを検知します。更新がleaseDurationSeconds(デフォルトでは40秒)を超えて途絶えると、Node ControllerはそのノードをNotReady状態と判断します。その後、その状態が継続すると、Node Controllerはそのノード上で動作しているPodを別の正常なノードへ再スケジュール(再配置)する処理を開始します。

kube-node-lease Namespaceに格納されているLeaseオブジェクトを確認します。ノードごとに1つのLeaseオブジェクトが存在し、Leaseオブジェクトの名前がノード名と同じであることがわかります。

[root@control ~]# kubectl get leases -n kube-node-lease
NAME      HOLDER    AGE
control   control   29d
worker1   worker1   29d
worker2   worker2   3d1h

次に、worker1ノードに対応するLeaseオブジェクトの内容を確認します。

[root@control ~]# kubectl get lease worker1 -n kube-node-lease -o yaml
apiVersion: coordination.k8s.io/v1
kind: Lease
metadata:
  creationTimestamp: "2026-06-05T05:37:30Z"
  name: worker1
  namespace: kube-node-lease
  ownerReferences:
  - apiVersion: v1
    kind: Node
    name: worker1
    uid: 8d828898-9282-4acd-b556-ceb068c8ff08
  resourceVersion: "132079"
  uid: a8fa8344-4044-47ff-9d3d-b94713364b29
spec:
  holderIdentity: worker1
  leaseDurationSeconds: 40
  renewTime: "2026-07-04T12:47:54.251743Z"

renewTimeの更新間隔を確認するため、LeaseオブジェクトのrenewTimeを1秒ごとに表示するrenewtime.shを作成して実行しました。
実行結果を見ると、renewTimeが約10秒ごとに更新されていることがわかります。このrenewTimeは、worker1ノード上で動作するkubeletによって定期的に更新されます。

[root@control ~]#  ./renewtime.sh
09:22:58   renewTime: "2026-07-05T00:22:54.205486Z"
09:22:59   renewTime: "2026-07-05T00:22:54.205486Z"
09:23:00   renewTime: "2026-07-05T00:22:54.205486Z"
09:23:01   renewTime: "2026-07-05T00:22:54.205486Z"
09:23:02   renewTime: "2026-07-05T00:22:54.205486Z"
09:23:03   renewTime: "2026-07-05T00:22:54.205486Z"
09:23:04   renewTime: "2026-07-05T00:22:54.205486Z"
09:23:05   renewTime: "2026-07-05T00:23:04.473769Z"
09:23:06   renewTime: "2026-07-05T00:23:04.473769Z"
09:23:07   renewTime: "2026-07-05T00:23:04.473769Z"
09:23:08   renewTime: "2026-07-05T00:23:04.473769Z"
09:23:09   renewTime: "2026-07-05T00:23:04.473769Z"
09:23:10   renewTime: "2026-07-05T00:23:04.473769Z"
09:23:11   renewTime: "2026-07-05T00:23:04.473769Z"
09:23:12   renewTime: "2026-07-05T00:23:04.473769Z"
09:23:13   renewTime: "2026-07-05T00:23:04.473769Z"
09:23:14   renewTime: "2026-07-05T00:23:14.799886Z"
09:23:15   renewTime: "2026-07-05T00:23:14.799886Z"
09:23:16   renewTime: "2026-07-05T00:23:14.799886Z"
09:23:17   renewTime: "2026-07-05T00:23:14.799886Z"
09:23:19   renewTime: "2026-07-05T00:23:14.799886Z"
09:23:20   renewTime: "2026-07-05T00:23:14.799886Z"
09:23:21   renewTime: "2026-07-05T00:23:14.799886Z"
09:23:22   renewTime: "2026-07-05T00:23:14.799886Z"
09:23:23   renewTime: "2026-07-05T00:23:14.799886Z"
09:23:24   renewTime: "2026-07-05T00:23:14.799886Z"
09:23:25   renewTime: "2026-07-05T00:23:24.830596Z"
09:23:26   renewTime: "2026-07-05T00:23:24.830596Z"

kubeletサービスを停止します。

[root@worker1 ~]# systemctl stop kubelet.service

kubeletサービスを停止すると、renewTimeが更新されなくなることが確認できます。これは、Leaseオブジェクトの更新をkubeletが行っていることを示しています。

[root@control ~]#  ./renewtime.sh
-snip-
09:23:23   renewTime: "2026-07-05T00:23:14.799886Z"
09:23:24   renewTime: "2026-07-05T00:23:14.799886Z"
09:23:25   renewTime: "2026-07-05T00:23:24.830596Z"
09:23:26   renewTime: "2026-07-05T00:23:24.830596Z"
09:23:27   renewTime: "2026-07-05T00:23:24.830596Z"
09:23:28   renewTime: "2026-07-05T00:23:24.830596Z"
09:23:29   renewTime: "2026-07-05T00:23:24.830596Z"
09:23:30   renewTime: "2026-07-05T00:23:24.830596Z"
09:23:31   renewTime: "2026-07-05T00:23:24.830596Z"
09:23:32   renewTime: "2026-07-05T00:23:24.830596Z"
09:23:33   renewTime: "2026-07-05T00:23:24.830596Z"
09:23:34   renewTime: "2026-07-05T00:23:24.830596Z"
09:23:35   renewTime: "2026-07-05T00:23:24.830596Z"
09:23:36   renewTime: "2026-07-05T00:23:24.830596Z"
09:23:37   renewTime: "2026-07-05T00:23:24.830596Z"
09:23:38   renewTime: "2026-07-05T00:23:24.830596Z"
09:23:39   renewTime: "2026-07-05T00:23:24.830596Z"
09:23:40   renewTime: "2026-07-05T00:23:24.830596Z"
09:23:41   renewTime: "2026-07-05T00:23:24.830596Z"
09:23:42   renewTime: "2026-07-05T00:23:24.830596Z"
09:23:44   renewTime: "2026-07-05T00:23:24.830596Z"

kubeletサービスを停止すると、LeaseオブジェクトのrenewTimeの更新が停止します。その後、一定時間が経過すると、kube-controller-managerが更新が止まったことを検知し、worker1ノードをNotReadyと判定します。

[root@control ~]# date;kubectl get nodes
2026年  7月  5日 日曜日 09:39:10 JST
NAME      STATUS   ROLES           AGE     VERSION
control   Ready    control-plane   29d     v1.35.5
worker1   Ready    <none>          29d     v1.35.5
worker2   Ready    <none>          3d13h   v1.35.5

[root@control ~]# date;kubectl get nodes
2026年  7月  5日 日曜日 09:39:16 JST
NAME      STATUS   ROLES           AGE     VERSION
control   Ready    control-plane   29d     v1.35.5
worker1   Ready    <none>          29d     v1.35.5
worker2   Ready    <none>          3d13h   v1.35.5

[root@control ~]# date;kubectl get nodes
2026年  7月  5日 日曜日 09:39:19 JST
NAME      STATUS     ROLES           AGE     VERSION
control   Ready      control-plane   29d     v1.35.5
worker1   NotReady   <none>          29d     v1.35.5
worker2   Ready      <none>          3d13h   v1.35.5

Z 参考図書

今回の記事執筆にあたり参考にした図書は以下のものです。

単行本

電子書籍