Kubernetes (MicroK8s)

本番環境での運用に対応している MicroK8sUbuntu 22.04 ホストマシンにインストール

MicroK8sのインストール(snap)

$ sudo snap install microk8s --classic
microk8s (1.25/stable) v1.25.2 from Canonical✓ installed

アドオンの有効化

$ sudo microk8s enable dns dashboard storage

アドオンの確認

$ sudo microk8s status --wait-ready
microk8s is running
high-availability: no
  datastore master nodes: 127.0.0.1:19001
  datastore standby nodes: none
addons:
  enabled:
    dashboard            # (core) The Kubernetes dashboard
    dns                  # (core) CoreDNS
    ha-cluster           # (core) Configure high availability on the current node
    helm                 # (core) Helm - the package manager for Kubernetes
    helm3                # (core) Helm 3 - the package manager for Kubernetes
    hostpath-storage     # (core) Storage class; allocates storage from host directory
    metrics-server       # (core) K8s Metrics Server for API access to service metrics
    storage              # (core) Alias to hostpath-storage add-on, deprecated
  disabled:
    cert-manager         # (core) Cloud native certificate management
    community            # (core) The community addons repository
    gpu                  # (core) Automatic enablement of Nvidia CUDA
    host-access          # (core) Allow Pods connecting to Host services smoothly
    ingress              # (core) Ingress controller for external access
    kube-ovn             # (core) An advanced network fabric for Kubernetes
    mayastor             # (core) OpenEBS MayaStor
    metallb              # (core) Loadbalancer for your Kubernetes cluster
    observability        # (core) A lightweight observability stack for logs, traces and metrics
    prometheus           # (core) Prometheus operator for monitoring and logging
    rbac                 # (core) Role-Based Access Control for authorisation
    registry             # (core) Private image registry exposed on localhost:32000

グループ micro8ks に現ユーザを追加、~/.kube へのアクセス権を付与(再ログイン後有効)

$ sudo usermod -a -G microk8s $USER
$ sudo chown -f -R $USER ~/.kube

microk8skubectlのみを使用する場合には下記エイリアスを設定(ログアウトすると無効)
常時有効にするためには ~/.bashrc に追加すること。

$ alias kubectl='microk8s kubectl'

ダッシュボードへのアクセス(URLの確認)
kube-system service/kubernetes-dashboard のIPアドレスとポートを確認してアクセス

$ sudo microk8s kubectl get all --all-namespaces
NAMESPACE     NAME                                             READY   STATUS    RESTARTS       AGE
kube-system   pod/calico-node-hfgdq                            1/1     Running   3 (102m ago)   3h30m
kube-system   pod/calico-kube-controllers-6ff488ffcf-wsrzb     1/1     Running   3 (102m ago)   3h30m
kube-system   pod/coredns-d489fb88-2zjdr                       1/1     Running   0              49m
kube-system   pod/dashboard-metrics-scraper-64bcc67c9c-9c9sw   1/1     Running   0              47m
kube-system   pod/metrics-server-6b6844c455-9rczd              1/1     Running   0              47m
kube-system   pod/kubernetes-dashboard-74b66d7f9c-flzbd        1/1     Running   0              47m
kube-system   pod/hostpath-provisioner-85ccc46f96-gjnkv        1/1     Running   0              47m
ingress       pod/nginx-ingress-microk8s-controller-xs4sm      1/1     Running   0              41m

NAMESPACE     NAME                                TYPE        CLUSTER-IP       EXTERNAL-IP   PORT(S)                  AGE
default       service/kubernetes                  ClusterIP   10.152.183.1     <none>        443/TCP                  3h30m
kube-system   service/kube-dns                    ClusterIP   10.152.183.10    <none>        53/UDP,53/TCP,9153/TCP   49m
kube-system   service/metrics-server              ClusterIP   10.152.183.96    <none>        443/TCP                  48m
kube-system   service/kubernetes-dashboard        ClusterIP   10.152.183.123   <none>        443/TCP                  48m
kube-system   service/dashboard-metrics-scraper   ClusterIP   10.152.183.18    <none>        8000/TCP                 48m

NAMESPACE     NAME                                               DESIRED   CURRENT   READY   UP-TO-DATE   AVAILABLE   NODE SELECTOR            AGE
kube-system   daemonset.apps/calico-node                         1         1         1       1            1           kubernetes.io/os=linux   3h30m
ingress       daemonset.apps/nginx-ingress-microk8s-controller   1         1         1       1            1           <none>                   41m

NAMESPACE     NAME                                        READY   UP-TO-DATE   AVAILABLE   AGE
kube-system   deployment.apps/calico-kube-controllers     1/1     1            1           3h30m
kube-system   deployment.apps/coredns                     1/1     1            1           49m
kube-system   deployment.apps/dashboard-metrics-scraper   1/1     1            1           48m
kube-system   deployment.apps/metrics-server              1/1     1            1           48m
kube-system   deployment.apps/kubernetes-dashboard        1/1     1            1           48m
kube-system   deployment.apps/hostpath-provisioner        1/1     1            1           48m

NAMESPACE     NAME                                                   DESIRED   CURRENT   READY   AGE
kube-system   replicaset.apps/calico-kube-controllers-54c85446d4     0         0         0       3h30m
kube-system   replicaset.apps/calico-kube-controllers-6ff488ffcf     1         1         1       3h30m
kube-system   replicaset.apps/coredns-d489fb88                       1         1         1       49m
kube-system   replicaset.apps/dashboard-metrics-scraper-64bcc67c9c   1         1         1       47m
kube-system   replicaset.apps/metrics-server-6b6844c455              1         1         1       47m
kube-system   replicaset.apps/kubernetes-dashboard-74b66d7f9c        1         1         1       47m
kube-system   replicaset.apps/hostpath-provisioner-85ccc46f96        1         1         1       47m

アクセストークンが必要なのでトークン microk8s-dashboard-token を読み取ります。

$ sudo microk8s kubectl -n kube-system get secret
NAME                              TYPE                                  DATA   AGE
kubernetes-dashboard-certs        Opaque                                0      43m
microk8s-dashboard-token          kubernetes.io/service-account-token   3      43m
kubernetes-dashboard-csrf         Opaque                                1      43m
kubernetes-dashboard-key-holder   Opaque                                2      43m

またはトークンを作成します (MicroK8s 1.24 以降)

$ microk8s kubectl create token default --duration=2h

kubectl create token reference
https://kubernetes.io/docs/reference/generated/kubectl/kubectl-commands#-em-token-em-

下記手順で表示されるトークンをダッシュボードの初期画面の既定箇所にコピーペーストして下さい。

$ token=$(sudo microk8s kubectl -n kube-system get secret | grep microk8s-dashboard-token | cut -d " " -f1)

$ sudo microk8s kubectl -n kube-system describe secret $token
.....
.....
token:      mNj99xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx
xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx
xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx
7z7g

Note) kubeconfig を指定する場合、~/.kube/config を入力します。~/.kube/config ファイルは $ microk8s config コマンドで作成されます。


ホストのポートをフォワーディングしてアクセスすることも出来ます。

$ microk8s kubectl port-forward -n kube-system service/kubernetes-dashboard 10443:443

上記コマンドでは、アクセスはローカルマシン限定となります。
外部からアクセスするためには、オプションで --address 0.0.0.0 を追加します。

URL : https://127.0.0.1:10443/

または以下の microk8s のコマンドでもダッシュボードへのアクセスは可能です(こちらは外部からデフォルトでアクセスできます)。

$ microk8s dashboard-proxy
Checking if Dashboard is running.
Infer repository core for addon dashboard
Waiting for Dashboard to come up.
Trying to get token from microk8s-dashboard-token
Waiting for secret token (attempt 0)
Dashboard will be available at https://127.0.0.1:10443
Use the following token to login:
eyJhbGciOiJSUzI.......................................
..............................................................
...............................................................SyrQg

ローカルのDockerイメージをmicrok8sへインポート

How to use a local registry
https://microk8s.io/docs/registry-images


microk8sのインスペクト:WARNING対応

$ microk8s inspect
......
......
WARNING:  Docker is installed. 
File "/etc/docker/daemon.json" does not exist. 
You should create it and add the following lines: 
{
    "insecure-registries" : ["localhost:32000"] 
}
and then restart docker with: sudo systemctl restart docker

WARNING:  The memory cgroup is not enabled. 
The cluster may not be functioning properly. Please ensure cgroups are enabled 
See for example: https://microk8s.io/docs/install-alternatives#heading--arm 

WARNING:  This machine's hostname contains capital letters and/or underscores. 
	  This is not a valid name for a Kubernetes node, causing node registration to fail.
	  Please change the machine's hostname or refer to the documentation for more details: 
	  https://microk8s.io/docs/troubleshooting#heading--common-issues 

WARNING: Docker is installed.

ローカルでビルドしたイメージを直接microk8sへ登録する場合に必要です。
(冒頭のローカルのDockerイメージをmicrok8sへインポートする手順を踏む場合には必要ありません)

How to use the built-in registry
https://microk8s.io/docs/registry-built-in

レジストリを有効化

$ microk8s enable registry

How to work with a private registry
https://microk8s.io/docs/registry-private

WireGuardとのコンフリクト

microk8s を起動すると kubernetes によるファイヤーウォールルールが iptables(iptables-legacy) に追加されるため WireGuard のネットワークが切断されます。このルールは microk8s を停止しても保持されるため、一度システムを再起動してルールをクリアにする必要があります。

影響しているファイヤーウォールルールは以下のコマンドで確認出来ます。

$ sudo iptables-legacy -L -v | grep -i kube
.....
.....

Chain KUBE-FIREWALL (2 references)
    0     0 DROP       all  --  any    any     anywhere             anywhere             /* kubernetes firewall for dropping marked packets */ mark match 0x8000/0x8000

.....
.....

以下何れかの対策を適用します。

(1) microk8sを停止してテーブルルールを削除

$ sudo iptables-legacy -D KUBE-FIREWALL -m comment --comment "kubernetes firewall for dropping marked packets" -m mark --mark 0x8000/0x8000 -j DROP

microk8s では iptables-legacy によりルールを適用 (xtables) しているため、他のアプリなどで iptables-legacy によるルールを利用していなければ全て削除して構いません。

$ sudo iptables-legacy -F

iptables-legacy, iptables-nft, nft の関係は以下の通り

+--------------+     +--------------+     +--------------+
|   iptables   |     |   iptables   |     |     nft      |   USER
|    legacy    |     |     nft      |     |  (nftables)  |   SPACE
+--------------+     +--------------+     +--------------+
       |                          |         |
====== | ===== KERNEL API ======= | ======= | =====================
       |                          |         |
+--------------+               +--------------+
|   iptables   |               |   nftables   |              KERNEL
|      API     |               |     API      |              SPACE
+--------------+               +--------------+
             |                    |         |
             |                    |         |
          +--------------+        |         |     +--------------+
          |   xtables    |--------+         +-----|   nftables   |
          |    match     |                        |    match     |
          +--------------+                        +--------------+

(2) /var/snap/microk8s/current/args/kube-apiserver に上記ファイヤーウォールルールを無効にする --bind-address=0.0.0.0 を追加して mikrok8s を起動

ホストの kubectl を使用する場合
https://microk8s.io/docs/working-with-kubectl

$ microk8s config
cd $HOME
mkdir .kube
cd .kube
microk8s config > config

よく使用するコマンド

* microk8s status: Provides an overview of the MicroK8s state (running / not running) as well as the set of enabled addons
* microk8s enable: Enables an addon
* microk8s disable: Disables an addon
* microk8s kubectl: Interact with kubernetes
* microk8s config: Shows the kubernetes config file
* microk8s istioctl: Interact with the istio services; needs the istio addon to be enabled
* microk8s inspect: Performs a quick inspection of the MicroK8s intallation
* microk8s reset: Resets the infrastructure to a clean state
* microk8s stop: Stops all kubernetes services
* microk8s start: Starts MicroK8s after it is being stopped

https://microk8s.io/docs/command-reference

ホストからダッシュボードへのポートフォワーディングとログインに必要なトークンを提示
https://127.0.0.1:10443 にアクセス

$ microk8s dashboard-proxy

上記コマンドは実質 $ kubectl port-foward と同義。--address 0.0.0.0 は外部からのアクセスを許可するオプション

$ kubectl port-forward -n kube-system service/kubernetes-dashboard 10443:443 --address 0.0.0.0

Multipassのインストール

Windows, macOS, Linux対応の仮想マシンマネージャでLinux版ではKVMを使用

snapでインストール

$ sudo snap install multipass

使用できるイメージ一覧

$ multipass find
Image                       Aliases           Version          Description
snapcraft:core18            18.04             20201111         Snapcraft builder for Core 18
snapcraft:core20            20.04             20210921         Snapcraft builder for Core 20
snapcraft:core22            22.04             20220426         Snapcraft builder for Core 22
snapcraft:devel                               20221004         Snapcraft builder for the devel series
core                        core16            20200818         Ubuntu Core 16
core18                                        20211124         Ubuntu Core 18
18.04                       bionic            20221003         Ubuntu 18.04 LTS
20.04                       focal             20221003         Ubuntu 20.04 LTS
22.04                       jammy,lts         20220923         Ubuntu 22.04 LTS
daily:22.10                 devel,kinetic     20220925         Ubuntu 22.10
appliance:adguard-home                        20200812         Ubuntu AdGuard Home Appliance
appliance:mosquitto                           20200812         Ubuntu Mosquitto Appliance
appliance:nextcloud                           20200812         Ubuntu Nextcloud Appliance
appliance:openhab                             20200812         Ubuntu openHAB Home Appliance
appliance:plexmediaserver                     20200812         Ubuntu Plex Media Server Appliance
anbox-cloud-appliance                         latest           Anbox Cloud Appliance
charm-dev                                     latest           A development and testing environment for charmers
docker                                        latest           A Docker environment with Portainer and related tools
jellyfin                                      latest           Jellyfin is a Free Software Media System that puts you in control of managing and streaming your media.
minikube                                      latest           minikube is local Kubernetes

上記イメージ core18 からインスタンスを起動

$ multipass launch core18
Launched: relished-finfoot   

インスタンスの確認

$ multipass list
Name                    State             IPv4             Image
relished-finfoot        Running           10.10.208.161    Ubuntu Core 18

上記インスタンス詳細

$ multipass info relished-finfoot
Name:           relished-finfoot
State:          Running
IPv4:           10.10.208.161
Release:        Core 18
Image hash:     0906153ddef6 (Ubuntu Core 18)
Load:           0.15 0.13 0.05
Disk usage:     55.6M out of 55.6M
Memory usage:   61.5M out of 985.0M
Mounts:         --

インスタンスのシェルへ移動

$ multipass shell relished-finfoot
Welcome to Ubuntu Core 18 (GNU/Linux 4.15.0-193-generic x86_64)
 * Ubuntu Core:     https://www.ubuntu.com/core
 * Community:       https://forum.snapcraft.io
 * Snaps:           https://snapcraft.io

This Ubuntu Core 18 machine is a tiny, transactional edition of Ubuntu,
designed for appliances, firmware and fixed-function VMs.

If all the software you care about is available as snaps, you are in
the right place. If not, you will be more comfortable with classic
deb-based Ubuntu Server or Desktop, where you can mix snaps with
traditional debs. It's a brave new world here in Ubuntu Core!

Please see 'snap --help' for app installation and updates.
Last login: Wed Oct  5 05:07:24 2022 from 10.10.208.1

ホストのシェルからコマンド実行

$ multipass exec relished-finfoot -- uname -a
Linux relished-finfoot 4.15.0-193-generic #204-Ubuntu SMP Fri Aug 26 19:20:21 UTC 2022 x86_64 x86_64 x86_64 GNU/Linux

インスタンスの停止(XXX→stop)、削除(XXX→delete)

$ multipass XXX relished-finfoot

完全削除

$ multipass purge

Multipassによる複数の仮想マシンの起動とノードとしての利用

Multipass により仮想マシンを複数起動(インスタンスを作成)し、Kubernetes のクラスターをこれら複数の仮想マシンで構築します。各仮想マシンをノードとして使用するため、各仮想マシンに MicroK8s をインストールします。

メモリ容量とインスタンス名を指定して仮想マシンを2台用意

デフォルトのイメージは以下のリリースで決めているようです。
https://cloud-images.ubuntu.com/releases/streams/v1/com.ubuntu.cloud:released:download.json

2台用意する場合には microk8s-node002 を追加して下さい。

$ multipass launch -m 2Gb -n microk8s-node001
Launched: microk8s-node001 

現時点でのデフォルトイメージは Ubuntu22.04 です。

$ multipass list
Name                    State             IPv4             Image
microk8s-node001        Running           10.10.208.215    Ubuntu 22.04 LTS

上記インスタンスのシェルに移動し MicroK8s をインストールします。

$ multipass shell microk8s-node001
Welcome to Ubuntu 22.04.1 LTS (GNU/Linux 5.15.0-48-generic x86_64)

 * Documentation:  https://help.ubuntu.com
 * Management:     https://landscape.canonical.com
 * Support:        https://ubuntu.com/advantage

 System information disabled due to load higher than 1.0


0 updates can be applied immediately.


The list of available updates is more than a week old.
To check for new updates run: sudo apt update

To run a command as administrator (user "root"), use "sudo <command>".
See "man sudo_root" for details.

MicroK8s のインストール

$ sudo snap install microk8s --classic
microk8s (1.25/stable) v1.25.2 from Canonical✓ installed

ユーザを microk8sグループに所属させ、~/.kube に所有権を付与します。

$ sudo usermod -a -G microk8s ubuntu
$ sudo chown -f -R ubuntu ~/.kube

一度ログアウトして再度ログインし上記設定を有効にします。

$ exit
$ multipass shell microk8s-node001

ホストマシンに MicroK8s をインストールしているため、これをマスターノードとし、microk8s-node001 をもう一台のマスターノードとしてクラスターに追加します。

ホストマシンで下記コマンドを実行すると、追加される側の仮想マシンで実行するコマンドが提示されます。トークン付きの下記コマンドの何れかを仮想マシン側のシェルで実行して下さい。

$ microk8s add-node
From the node you wish to join to this cluster, run the following:
microk8s join 192.168.1.214:25000/1d0ecd931df556986b26ec6dc8397ae1/0acdef7ccecc

Use the '--worker' flag to join a node as a worker not running the control plane, eg:
microk8s join 192.168.1.214:25000/1d0ecd931df556986b26ec6dc8397ae1/0acdef7ccecc --worker

If the node you are adding is not reachable through the default interface you can use one of the following:
microk8s join 192.168.1.214:25000/1d0ecd931df556986b26ec6dc8397ae1/0acdef7ccecc
microk8s join 192.168.122.1:25000/1d0ecd931df556986b26ec6dc8397ae1/0acdef7ccecc
microk8s join 172.17.0.1:25000/1d0ecd931df556986b26ec6dc8397ae1/0acdef7ccecc
microk8s join 192.168.49.1:25000/1d0ecd931df556986b26ec6dc8397ae1/0acdef7ccecc
microk8s join 10.10.208.1:25000/1d0ecd931df556986b26ec6dc8397ae1/0acdef7ccecc
microk8s join fdff:f679:25e0::ca2:25000/1d0ecd931df556986b26ec6dc8397ae1/0acdef7ccecc
microk8s join fdff:f679:25e0:0:4dd7:905a:9cba:50f7:25000/1d0ecd931df556986b26ec6dc8397ae1/0acdef7ccecc
microk8s join fdff:f679:25e0:0:cbc4:6813:e183:7b0e:25000/1d0ecd931df556986b26ec6dc8397ae1/0acdef7ccecc

仮想マシン上で上記提示されたコマンドを実行

$ microk8s join 192.168.1.214:25000/678c6b4b9f561da9bbc23bd59031ed52/0acdef7ccecc
Contacting cluster at 192.168.1.214
Connection failed. The hostname (microk8s-node001) of the joining node does not resolve to the IP "10.10.208.215". Refusing join (400).

上記エラーが表示された場合、ホスト側でIPアドレスの名前解決をして下さい。

$ sudo nano /etc/hosts
......
......
10.10.208.215   microk8s-node001
......
......

ダッシュボードで仮想マシンで動作しているポッドの確認

各ノードにリソース(ポッド)がどのように割当てられているか確認して下さい。

Multipass エラー

launch failed: Remote "" is unknown or unreachable.

$ multipass launch -m 2Gb -n microk8s-node002         
launch failed: Remote "" is unknown or unreachable.  

multipass の再起動

再起動するサービスの確認

$ sudo snap services
Service                                              Startup   Current   Notes
microk8s.daemon-apiserver-kicker                     disabled  inactive  -
microk8s.daemon-apiserver-proxy                      disabled  inactive  -
microk8s.daemon-cluster-agent                        disabled  inactive  -
microk8s.daemon-containerd                           disabled  inactive  -
microk8s.daemon-etcd                                 disabled  inactive  -
microk8s.daemon-flanneld                             disabled  inactive  -
microk8s.daemon-k8s-dqlite                           disabled  inactive  -
microk8s.daemon-kubelite                             disabled  inactive  -
multipass.multipassd                                 enabled   active    -
snapd-desktop-integration.snapd-desktop-integration  enabled   -         user

multipass サービス再起動

$ sudo snap restart multipass.multipassd
2022-10-06T09:49:22+09:00 INFO Waiting for "snap.multipass.multipassd.service" to stop.
Restarted.

Services and ports

https://microk8s.io/docs/services-and-ports

Services binding to the default Host interface

PORT SERVICE ACCESS RESTRICTIONS
16443 API server SSL encrypted. Clients need to present a valid password from a Static Password File.
10250 kubelet Anonymous authentication is disabled. X509 client certificate is required.
10255 kubelet Read only port for the Kubelet.
25000 cluster-agent Proper token required to authorise actions.
12379 etcd SSL encrypted. Client certificates required to connect.
10257 kube-controller Serve HTTPS with authentication and authorization.
10259 kube-scheduler Serve HTTPS with authentication and authorization.
19001 dqlite SSL encrypted. Client certificates required to connect.
4789/udp calico Calico networking with VXLAN enabled.

Services binding to the localhost interface

PORT SERVICE DESCRIPTION
10248 kubelet Localhost healthz endpoint.
10249 kube-proxy Port for the metrics server to serve on.
10251 kube-schedule Port on which to serve HTTP insecurely.
10252 kube-controller Port on which to serve HTTP insecurely.
10256 kube-proxy Port to bind the health check server.
2380 etcd Used for peer connections.
1338 containerd Metrics port

The authentication strategies enabled by default are:

  • Static Token File with tokens in /var/snap/microk8s/current/credentials/known_tokens.csv
  • X509 Client Certs with the client CA file set to /var/snap/microk8s/current/certs/ca.crt

Under /var/snap/microk8s/current/credentials/ you can find the client.config kubeconfig file used by microk8s kubectl .

Multipassで作成した仮想マシンのみでクラスターを作成

前回の投稿記事ではホストと仮想マシンでクラスターを構築しましたが、今回はホストマシンにインストールしたmicrok8sを停止、Multipassで作成した複数の仮想マシンでクラスターを構築します。

1台目の仮想マシン

以下の手順でmultipassで1台目の仮想マシンを用意。ダッシュボードを有効にするとデフォルトの容量4.7GBでは不足します。ディスク容量も指定して作成した方が良いでしょう

$ multipass launch -d 20G -m 2Gb -n microk8s-node001 
$ multipass start microk8s-node001
$ multipass list
Name                    State             IPv4             Image
microk8s-node001        Running           10.10.208.25     Ubuntu 22.04 LTS

上記仮想マシンのシェルでmicrok8sのインストールと拡張機能の有効化を実施

$ multipass shell microk8s-node001

以下仮想マシンのシェル

microk8s-node001:~$ sudo snap install microk8s --classic
microk8s-node001:~$ sudo usermod -a -G microk8s $USER
microk8s-node001:~$ sudo chown -f -R $USER ~/.kube
microk8s-node001:~$ exit

仮想マシンのシェルへ再ログイン(IPテーブルによりホストとVM間の通信許可)

$ multipass shell microk8s-node001
microk8s-node001:~$ sudo iptables -P FORWARD ACCEPT

dashboard storage dnsを有効化

microk8s-node001:~$ microk8s enable dashboard storage dns

コマンドのエイリアス作成

microk8s-node001:~$ alias kubectl='microk8s kubectl'

ダッシュボードのIPとポートを確認

microk8s-node001:~$ kubectl get svc -n kube-system
NAME                        TYPE        CLUSTER-IP       EXTERNAL-IP   PORT(S)                  AGE
metrics-server              ClusterIP   10.152.183.235   <none>        443/TCP                  11m
kubernetes-dashboard        ClusterIP   10.152.183.21    <none>        443/TCP                  10m
dashboard-metrics-scraper   ClusterIP   10.152.183.22    <none>        8000/TCP                 10m
kube-dns                    ClusterIP   10.152.183.10    <none>        53/UDP,53/TCP,9153/TCP   10m

事前にアクセストークンを入手します

microk8s-node001:~$ kubectl create token default

ホストのウェブブラウザからダッシュボードへアクセスするため、仮想マシン上でポートフォワーディングする必要があります。(外部からのアクセスを許可 --address 0.0.0.0

microk8s-node001:~$ kubectl port-forward -n kube-system service/kubernetes-dashboard 10443:443 --address 0.0.0.0
Forwarding from 0.0.0.0:10443 -> 8443
Handling connection for 10443
Handling connection for 10443
........

ホストから https://<NODE_IP>:10443 を入力するとトークン入力画面が表示されるので先程入手したトークンを入力します。

Accessing Dashboard


2台目、3台目の仮想マシン

2台目(microk8s-node002)、3台目(microk8s-node003)のインスタンスも同様に作成しmicrok8sをインストールします。

Note) インストール時や起動時にエラーが発生する場合には、一度インスタンスを再起動して再度インストールまたは起動コマンドを実行してみて下さい。

$ microk8s start
error: error running snapctl: cannot perform the following tasks:
- Run service command "start" for services ["daemon-apiserver-kicker" "daemon-apiserver-proxy" "daemon-cluster-agent" "daemon-containerd" "daemon-etcd" "daemon-flanneld" "daemon-k8s-dqlite" "daemon-kubelite"] of snap "microk8s" (systemctl command [start snap.microk8s.daemon-containerd.service] failed with exit status 1: Job for snap.microk8s.daemon-containerd.service failed because a timeout was exceeded.
See "systemctl status snap.microk8s.daemon-containerd.service" and "journalctl -xeu snap.microk8s.daemon-containerd.service" for details.
)
Failed to start microk8s services. Check snapd logs with "journalctl -u snapd.service"

仮想マシンをノードとして追加

1台目の仮想マシンをマスターノードとし、2台目、3台目の仮想マシンをワーカノードとしてクラスターに追加します。

マスターノードとする1台目の仮想マシンで、ワーカノードで実行するコマンド(マスターノードのトークン付きIPアドレスが表示)を提示します。トークンは一度のみ有効なので、2度提示する必要があります。

$ microk8s add-node
From the node you wish to join to this cluster, run the following:
microk8s join 10.10.208.26:25000/6dcdbea8f2e8d94a67ccc0d6446ff564/fc2d9e458a80

Use the '--worker' flag to join a node as a worker not running the control plane, eg:
microk8s join 10.10.208.26:25000/6dcdbea8f2e8d94a67ccc0d6446ff564/fc2d9e458a80 --worker

If the node you are adding is not reachable through the default interface you can use one of the following:
microk8s join 10.10.208.26:25000/6dcdbea8f2e8d94a67ccc0d6446ff564/fc2d9e458a80

2台目、3台目の仮想マシン上で、各々をワーカノードとしてマスターノード側のクラスターに追加します。

$ microk8s join 10.10.208.26:25000/6dcdbea8f2e8d94a67ccc0d6446ff564/fc2d9e458a80 --worker
Contacting cluster at 10.10.208.26

The node has joined the cluster and will appear in the nodes list in a few seconds.

This worker node gets automatically configured with the API server endpoints.
If the API servers are behind a loadbalancer please set the '--refresh-interval' to '0s' in:
    /var/snap/microk8s/current/args/apiserver-proxy
and replace the API server endpoints with the one provided by the loadbalancer in:
    /var/snap/microk8s/current/args/traefik/provider.yaml

マスターノードのダッシュボードでクラスターに追加されたノードを確認(node001, node002, node003を上記ノードの名称に置換えています)

マスターノードのシェルで確認

$ kubectl get node
NAME      STATUS   ROLES    AGE     VERSION
node001   Ready    <none>   4h15m   v1.25.2
node002   Ready    <none>   19m     v1.25.2
node003   Ready    <none>   7m49s   v1.25.2

Note) ワーカノードとしてマスターノードに取り込まれた仮想マシンのシェルでkubectlコマンドの使用はできません。マスターのみコマンドを実行できます。

参考)


追加したノードを元の独立したノードに戻す場合
node002またはnode003のシェル内で以下コマンドを実行

$ microk8s leave

クラスターからノードを削除する場合(node002を除外)は
node001のシェル内で以下のコマンドを実行

$ microk8s remove-node node002

Multipass :インスタンスのディスク容量変更

既に作成したインスタンスのディスク容量が不足した場合は以下の手順で拡張が可能です。

インスタンスを停止

$ multipass stop INSTANCE_NAME 

インスタンスが使用しているイメージを検索します

$ sudo find /var/snap -type d -name multipassd
[sudo] takanobu のパスワード: 
/var/snap/multipass/common/data/multipassd
/var/snap/multipass/common/cache/multipassd
/var/snap/multipass/7967/config/multipassd

以下のディレクトリに移動し格納されているインスタンスの元イメージを確認

$ cd /var/snap/multipass/common/data/multipassd/vault/instances/INSTANCE_NAME
$ ls
cloud-init-config.iso  ubuntu-22.04-server-cloudimg-amd64.img

20GB追加(qemu-img)

$ sudo qemu-img resize ubuntu-22.04-server-cloudimg-amd64.img +20G

インスタンスを起動します。

$ cd
$ multipass start INSTANCE_NAME

クラスターにNginxをデプロイ

デプロイとサービスを同一ファイルに記述

nginx-app.yaml

apiVersion: v1
kind: Service
metadata:
  name: my-nginx-svc
  labels:
    app: nginx
spec:
  type: LoadBalancer
  ports:
  - port: 80
  selector:
    app: nginx
---
apiVersion: apps/v1
kind: Deployment
metadata:
  name: my-nginx
  labels:
    app: nginx
spec:
  replicas: 3
  selector:
    matchLabels:
      app: nginx
  template:
    metadata:
      labels:
        app: nginx
    spec:
      containers:
      - name: nginx
        image: nginx:1.14.2
        ports:
        - containerPort: 80

上記マニフェストを適用

$ kubectl apply -f https://k8s.io/examples/application/nginx-app.yaml
service/my-nginx-svc created
deployment.apps/my-nginx created

Nginxポッドとサービスの確認(3レプリカ)

$ kubectl get svc,pod
NAME                   TYPE           CLUSTER-IP       EXTERNAL-IP   PORT(S)        AGE
service/kubernetes     ClusterIP      10.152.183.1     <none>        443/TCP        6h29m
service/my-nginx-svc   LoadBalancer   10.152.183.251   <pending>     80:32177/TCP   82s

NAME                            READY   STATUS              RESTARTS   AGE
pod/my-nginx-7fb96c846b-cfd6k   0/1     ContainerCreating   0          67s
pod/my-nginx-7fb96c846b-58mp5   0/1     ContainerCreating   0          69s
pod/my-nginx-7fb96c846b-6xk9f   0/1     ContainerCreating   0          67s

各ノードのIPアドレスの確認

$ multipass list
Name                    State             IPv4             Image
node001                 Running           10.10.208.26     Ubuntu 22.04 LTS
                                          10.1.152.128
node002                 Running           10.10.208.13     Ubuntu 22.04 LTS
                                          10.1.112.128
node003                 Running           10.10.208.59     Ubuntu 22.04 LTS
                                          10.1.67.193

ホストマシンのブラウザからは、各ノードのIPアドレスとサービスで提示されたポート32177でアクセスできます。

  • node001 : http://10.10.208.26:32177
  • node002 : http://10.10.208.13:32177
  • node003 : http://10.10.208.59:32177

cert-manager

以下の認証局からTLS認証手続きを自動で実行するKubernetesのアドオン

Let’s Encrypt
HashiCorp Vault
Venafi

GitHub

high-level-overview

Helmによる公式パッケージ


ACME

The ACME Issuer type represents a single account registered with the Automated Certificate Management Environment (ACME) Certificate Authority server. When you create a new ACME Issuer , cert-manager will generate a private key which is used to identify you with the ACME server.

HTTP01 challenges are completed by presenting a computed key, that should be present at a HTTP URL endpoint and is routable over the internet. This URL will use the domain name requested for the certificate. Once the ACME server is able to get this key from this URL over the internet, the ACME server can validate you are the owner of this domain. When a HTTP01 challenge is created, cert-manager will automatically configure your cluster ingress to route traffic for this URL to a small web server that presents this key.

DNS01 challenges are completed by providing a computed key that is present at a DNS TXT record. Once this TXT record has been propagated across the internet, the ACME server can successfully retrieve this key via a DNS lookup and can validate that the client owns the domain for the requested certificate. With the correct permissions, cert-manager will automatically present this TXT record for your given DNS provider.


トラブルシュート

Troubleshooting Problems with ACME / Let’s Encrypt Certificates

kubectlコマンドリファレンス

kubectl expose

https://kubernetes.io/docs/reference/generated/kubectl/kubectl-commands#expose

Create a service for a replicated nginx, which serves on port 80 and connects to the containers on port 8000

$ kubectl expose rc nginx --port=80 --target-port=8000

Create a service for a replication controller identified by type and name specified in “nginx-controller.yaml”, which serves on port 80 and connects to the containers on port 8000

$ kubectl expose -f nginx-controller.yaml --port=80 --target-port=8000

Create a service for a pod valid-pod, which serves on port 444 with the name “frontend”

$ kubectl expose pod valid-pod --port=444 --name=frontend

Create a second service based on the above service, exposing the container port 8443 as port 443 with the name “nginx-https”

$ kubectl expose service nginx --port=443 --target-port=8443 --name=nginx-https

Create a service for a replicated streaming application on port 4100 balancing UDP traffic and named ‘video-stream’.

$ kubectl expose rc streamer --port=4100 --protocol=UDP --name=video-stream

Create a service for a replicated nginx using replica set, which serves on port 80 and connects to the containers on port 8000

$ kubectl expose rs nginx --port=80 --target-port=8000

Create a service for an nginx deployment, which serves on port 80 and connects to the containers on port 8000

$ kubectl expose deployment nginx --port=80 --target-port=8000

kubectl port-foward

https://kubernetes.io/docs/reference/generated/kubectl/kubectl-commands#port-forward

Kubernetesクラスターをインストールしたホストマシンに外部からアクセスする際などに必要となる措置。

Listen on ports 5000 and 6000 locally, forwarding data to/from ports 5000 and 6000 in the pod

$ kubectl port-forward pod/mypod 5000 6000

Listen on ports 5000 and 6000 locally, forwarding data to/from ports 5000 and 6000 in a pod selected by the deployment

$ kubectl port-forward deployment/mydeployment 5000 6000

Listen on port 8443 locally, forwarding to the targetPort of the service’s port named “https” in a pod selected by the service

$ kubectl port-forward service/myservice 8443:https

Listen on port 8888 locally, forwarding to 5000 in the pod

$ kubectl port-forward pod/mypod 8888:5000

Listen on port 8888 on all addresses, forwarding to 5000 in the pod

$ kubectl port-forward --address 0.0.0.0 pod/mypod 8888:5000

Listen on port 8888 on localhost and selected IP, forwarding to 5000 in the pod

$ kubectl port-forward --address localhost,10.19.21.23 pod/mypod 8888:5000

Listen on a random port locally, forwarding to 5000 in the pod

$ kubectl port-forward pod/mypod :5000

kubectl proxy

https://kubernetes.io/docs/reference/generated/kubectl/kubectl-commands#proxy

ローカルホストからKubernetesのAPIサーバへアクセスするためのプロキシーサーバを作成するためのコマンド

To proxy all of the Kubernetes API and nothing else

$ kubectl proxy --api-prefix=/

To proxy only part of the Kubernetes API and also some static files # You can get pods info with ‘curl localhost:8001/api/v1/pods’

$ kubectl proxy --www=/my/files --www-prefix=/static/ --api-prefix=/api/

To proxy the entire Kubernetes API at a different root # You can get pods info with ‘curl localhost:8001/custom/api/v1/pods’

$ kubectl proxy --api-prefix=/custom/

Run a proxy to the Kubernetes API server on port 8011, serving static content from ./local/www/

$ kubectl proxy --port=8011 --www=./local/www/

Run a proxy to the Kubernetes API server on an arbitrary local port # The chosen port for the server will be output to stdout

$ kubectl proxy --port=0

Run a proxy to the Kubernetes API server, changing the API prefix to k8s-api # This makes e.g. the pods API available at localhost:8001/k8s-api/v1/pods/

$ kubectl proxy --api-prefix=/k8s-api

kubernetes設定ファイル ($ kubectl config view)

kubernetes設定ファイルは、clusters, contexts, users の3つのセクションから構成されます。別記事 Kubernetes (minikube) - tk-fuse の #9 で取り上げたminicubeによるkubernetes設定ファイルには、ダッシュボードへアクセスする際のIPアドレス、ポートとTLS認証ファイルのディレクトリなどが予め設定されていたため、ダッシュボードへアクセスする際にログイン画面は表示されませんでしたが、下記のmicrok8sによる設定ファイルでは、それら設定が定義されていないため、ログイン画面が表示されトークンの入力が求められます(セキュリティ上はこちらが正)。

clusters, contexts, users の3つのセクションに新たな項目(クラスター、コンテクスト、ユーザ)を登録することで、より細かなシステム管理が出来るようになります。

microk8s デフォルト設定ファイル ~/.kube/config

$ kubectl config view

apiVersion: v1
clusters:
- cluster:
    certificate-authority-data: DATA+OMITTED
    server: https://127.0.0.1:16443
  name: microk8s-cluster
contexts:
- context:
    cluster: microk8s-cluster
    user: admin
  name: microk8s
current-context: microk8s
kind: Config
preferences: {}
users:
- name: admin
  user:
    token: REDACTED

minikube デフォルト設定ファイル ~/.kube/config

$ kubectl config view

apiVersion: v1
clusters:
- cluster:
    certificate-authority: /home/student/.minikube/ca.crt
    server: https://192.168.99.100:8443
  name: minikube
contexts:
- context:
    cluster: minikube
    user: minikube
  name: minikube
current-context: minikube
kind: Config
preferences: {}
users:
- name: minikube
  user:
    client-certificate: /home/student/.minikube/profiles/minikube/client.crt
    client-key: /home/student/.minikube/profiles/minikube/client.key

サービスリソース詳細

サービスリソース一覧からサービスを指定して、その詳細を確認(IPとポート確認)

$ kubectl get svc --all-namespaces
NAMESPACE     NAME                        TYPE        CLUSTER-IP       EXTERNAL-IP   PORT(S)                  AGE
default       kubernetes                  ClusterIP   10.152.183.1     <none>        443/TCP                  29h
kube-system   metrics-server              ClusterIP   10.152.183.136   <none>        443/TCP                  29h
kube-system   kubernetes-dashboard        ClusterIP   10.152.183.99    <none>        443/TCP                  29h
kube-system   dashboard-metrics-scraper   ClusterIP   10.152.183.190   <none>        8000/TCP                 29h
kube-system   kube-dns                    ClusterIP   10.152.183.10    <none>        53/UDP,53/TCP,9153/TCP   28h

サービス:ダッシュボードの詳細確認(エンドポイントのIPとポートの確認)

$ kubectl describe svc/kubernetes-dashboard -n kube-system
Name:              kubernetes-dashboard
Namespace:         kube-system
Labels:            k8s-app=kubernetes-dashboard
Annotations:       <none>
Selector:          k8s-app=kubernetes-dashboard
Type:              ClusterIP
IP Family Policy:  SingleStack
IP Families:       IPv4
IP:                10.152.183.99
IPs:               10.152.183.99
Port:              <unset>  443/TCP
TargetPort:        8443/TCP
Endpoints:         10.1.237.136:8443
Session Affinity:  None
Events:            <none>

エンドポイント情報は以下の get コマンドでも取得可能(ラベルオプション追加)

$ kubectl get ep --all-namespaces --show-labels
NAMESPACE     NAME                        ENDPOINTS                                           AGE   LABELS
default       kubernetes                  10.10.208.97:16443                                  31h   endpointslice.kubernetes.io/skip-mirror=true
kube-system   kubernetes-dashboard        10.1.237.136:8443                                   30h   k8s-app=kubernetes-dashboard
kube-system   kube-dns                    10.1.237.135:53,10.1.237.135:53,10.1.237.135:9153   30h   addonmanager.kubernetes.io/mode=Reconcile,k8s-app=kube-dns,kubernetes.io/cluster-service=true,kubernetes.io/name=CoreDNS
kube-system   dashboard-metrics-scraper   10.1.237.138:8000                                   30h   k8s-app=dashboard-metrics-scraper
kube-system   metrics-server              10.1.237.140:4443                                   30h   k8s-app=metrics-server
kube-system   microk8s.io-hostpath        <none>                                              30h   <none>

インスタンス .bashrc

minicubeの記事 Kubernetes (minikube) - tk-fuse の #26 でも記述しましたが、インスタンスのシェル起動時に kubectl コマンドへのカスタマイズが反映されるよう.bashrcに以下の項目(標準編集アプリとコマンドエイリアス)を追加します(再ログイン必要)。

~/.bashrc

..........
..........
alias kubectl='microk8s kubectl'
export KUBE_EDITOR=/usr/bin/nano