kubeadmでのKubernetes構築トラブルシューティング

##本記事の目的
下記のKubernetes公式ドキュメントを用いて、社内でkubeadmによるk8sの構築を実施した際に、ドキュメント情報のみでは解決できなかったトラブルについて記す。

・公式ドキュメントでのkubeadmによる構築手順
①[CRIのインストール](https://kubernetes.io/ja/docs/setup/production-environment/container-runtimes/)
②[kubeadmのインストール](https://kubernetes.io/ja/docs/setup/production-environment/tools/kubeadm/install-kubeadm/)
③[kubeadmを使用したシングルコントロールプレーンクラスターの作成](https://kubernetes.io/ja/docs/setup/production-environment/tools/kubeadm/create-cluster-kubeadm/)


##トラブルその1: スワップ領域の無効化
②kubeadmのインストール"に以下の記載がある。
>Swapがオフであること。kubeletが正常に動作するためにはswapは必ずオフでなければなりません。

スワップ領域を一時的に無効化するならば、rootユーザーで以下のコマンドを実施すれば良い。

```
$ swapoff -a
```

また、一部のシステム構成では、/etc/fstabのswap領域に関する行を全てコメントアウトする事で恒久的にスワップ領域を無効化することができる。

```txt:/etc/fstab
# /dev/mapper/xxx-swap swap                    swap    defaults        0 0
```

<br>
しかし、システム構成によっては、ノードを再起動すると再度スワップ領域が有効化されてしまい、以下のようにkubeletが正常に起動しなくなる事がある。
特にUbuntuでのシステム構成において多発する印象を持つ。

```
$ systemctl status kubelet
● kubelet.service - kubelet: The Kubernetes Node Agent
Loaded: loaded (/usr/lib/systemd/system/kubelet.service; enabled; vendor preset: disabled)
Drop-In: /usr/lib/systemd/system/kubelet.service.d
mq10-kubeadm.conf
Active: activating (auto-restart) (Result: exit-code) since 日 2020-11-15 15:36:04 JST; 1s ago
Docs: https://kubernetes.io/docs/
Process: 8060 ExecStart=/usr/bin/kubelet $KUBELET_KUBECONFIG_ARGS $KUBELET_CONFIG_ARGS $KUBELET_KUBEADM_ARGS $KUBELET_EXTRA_ARGS (code=exited, status=255)
Main PID: 8060 (code=exited, status=255)
```

またこの状態でkubectl get nodesコマンドを実施すると、kubeletが正常に起動していないノードのステータスがNot Readyと表示される。

```
$ kubectl get nodes
NAME        STATUS    ROLES   AGE  VERSION
k8s-master  Ready     master  14d  v1.19.3
k8s-worker  NotReady  <none>  14d  v1.19.3
```

<br>
この場合、恒久的にスワップ領域を無効化するには、以下の記事を参照すると良い。

https://qiita.com/10yama/items/1ab36a638c6e5c11c136

<br>

##トラブルその2: クラスターに関する権限付与
「③kubeadmを使用したシングルコントロールプレーンクラスターの作成」に以下の記載がある。

>kubectlをroot以外のユーザーでも実行できるようにするには、次のコマンドを実行します。これらのコマンドは、kubectl initの出力の中にも書かれています。


>```
$ mkdir -p $HOME/.kube
$ sudo cp -i /etc/kubernetes/admin.conf $HOME/.kube/config
$ sudo chown $(id -u):$(id -g) $HOME/.kube/config
```

>あなたがrootユーザーである場合は、代わりに次のコマンドを実行します。

>```
$ export KUBECONFIG=/etc/kubernetes/admin.conf
```

<br>

ここで、rootユーザーとして後者のexportコマンドを実施して設定すると、ノードを再起動した際に設定が初期化されてしまい、クラスターに関する権限が正しく付与されないという問題が生じる。

この権限が付与されていない場合、kubectl get nodesコマンドを実施した際に、以下の表示が現れる事がある。

```
$ kubectl get nodes
The connection to the server localhost:6443 was refused - did you specify the right host or port?
```

<br>
解決方法としては、スワップ領域の無効化と同じく、rootユーザーのログインシェルにexprotコマンドを書き込めば良い。

```
$ cat << EOF >> ~/.bach_profile
> export KUBECONFIG=/etc/kubernetes/admin.conf
> EOF

$ exec $SHELL -l
```

<br>

##トラブルその3: 名前解決
公式ドキュメントでのkubeadmによる構築手順に明確な記載はないものの、k8s構築を完了させるにはマスターノード及びワーカーノードの名前解決が必要となる。

名前解決のレコードが不足している場合、ワーカーノード上でkubeadm joinコマンド実施後に、マスターノード上でkubectl get nodesコマンドを実施しても、ワーカーノードの情報が表示されない事がある。


```
$ kubeadm join --token <token> <control-plane-host>:<control-plane-port> --discovery-token-ca-cert-hash sha256:<hash>
```

```
$ kubectl get nodes
NAME        STATUS    ROLES   AGE  VERSION
k8s-master  Ready     master  14d  v1.19.3
```

<br>

簡易的に解決したいのであれば、全てのノードの/etc/hostsファイルに該当するマスターノード及びワーカーノードのレコードを追記すれば良い。
(/etc/hostsは変更時に設定を即座に反映するため、再ログインの必要はない)

```
$ cat << EOF >> /etc/hosts
> 10.0.0.1   k8s-master
> 10.0.0.2   k8s-worker
> EOF
```

またDNSサーバを使用しているのであれば、DNSサーバに該当するマスターノード及びワーカーノードのレコード設定を追加する事で解決する。


##まとめ
本記事ではkubeadmによるk8s構築のトラブルシューティングのポイントについて解説した。
kubeadmによる構築は、事前にLinux側で設定する箇所が多く、またトラブルシューティングにもLinuxの知見が要求されるため、個人的にはlPICレベル1程度の知識を身につけてから実施する事をオススメする。