[小ネタ]KubernetesでnodeName指定のPodデプロイはスケジューリングを無視する

# はじめに
KubernetesでPodをデプロイするYAMLファイルでは様々な値を指定することができますが、その中に```nodeName```というものがあります。```nodeName```では特定のNodeを指定することで、そのNodeに対してPodをデプロイすることができます。今回はこの```nodeName```について、簡単に紹介したいと思います。

# nodeNameとは

早速```nodeName```を使ってみます。なお利用している環境は[こちらの記事](https://qiita.com/FY0323/items/0815ec98ddcd2f95d469)と同様になります。

YAMLファイルでは以下のように記述します。

```sample-nodename.yaml
apiVersion: v1
kind: Pod
metadata:
  name: sample-nodename
spec:
  containers:
  - name: nginx-container
    image: nginx:1.12
  nodeName: kube-worker01  # PodSpecで指定する
```

さて、```nodeName```を指定した場合、KubernetesのschedulerはこのPodを「無視」し、指定したNode上のkubeletはこのPodをデプロイしようと試みます。そのため、通常Podをデプロイした場合とは異なり、「どのNodeにデプロイしようか」というスケジューリングが働きません。

試しに```nodeName```で指定したNodeをcordonでスケジュール対象外とした場合を見てみます。

```sh
# kube-worker01をcordon
[root@kube-master01 ~]# kubectl cordon kube-worker01
node/kube-worker01 cordoned
[root@kube-master01 ~]# kubectl get nodes
NAME            STATUS                     ROLES    AGE   VERSION
kube-master01   Ready                      master   9d    v1.15.1
kube-worker01   Ready,SchedulingDisabled   <none>   9d    v1.15.1
kube-worker02   Ready                      <none>   9d    v1.15.1
[root@kube-master01 ~]#

# Podデプロイ
[root@kube-master01 ~]# kubectl apply -f sample-nodename.yaml
pod/sample-nodename created
[root@kube-master01 ~]#

# 確認
[root@kube-master01 ~]# kubectl get pods -o wide
NAME              READY   STATUS    RESTARTS   AGE   IP               NODE            NOMINATED NODE   READINESS GATES
sample-nodename   1/1     Running   0          7s    192.168.132.59   kube-worker01   <none>           <none>
[root@kube-master01 ~]#
```

御覧の通り、**スケジューリング対象外のNodeにデプロイができてしまいました**。通常cordon/uncordonなどで特定のNodeのスケジューリングをコントロールする場合、そのNodeに対してPodがデプロイされては困る（もしくはPodが動作しない）ような状況だと思われます。しかし```nodeName```を指定している場合、それを無視してPodがデプロイされてしまいます。そのため、**あるPodを特定のNodeにデプロイしたい場合、基本的に```nodeName```は利用せず、labelなどを利用したスケジューリングを検討するほうが良い**と思います。

なお、```nodeName```で指定したNodeが停止している場合、デプロイしたPodは```Pending```となります。

```sh
# Node停止
>vagrant halt kube-worker01
>vagrant status
Current machine states:

kube-master01             running (virtualbox)
kube-worker01             poweroff (virtualbox)
kube-worker02             running (virtualbox)
kube-client               running (virtualbox)

[root@kube-master01 ~]# kubectl get nodes
NAME            STATUS                        ROLES    AGE   VERSION
kube-master01   Ready                         master   9d    v1.15.1
kube-worker01   NotReady,SchedulingDisabled   <none>   9d    v1.15.1
kube-worker02   Ready                         <none>   9d    v1.15.1

# Podデプロイ
[root@kube-master01 ~]# kubectl apply -f sample-nodename.yaml
pod/sample-nodename created
[root@kube-master01 ~]#

# 確認
[root@kube-master01 ~]# kubectl get pods -o wide
NAME              READY   STATUS    RESTARTS   AGE   IP       NODE            NOMINATED NODE   READINESS GATES
sample-nodename   0/1     Pending   0          5s    <none>   kube-worker01   <none>           <none>
[root@kube-master01 ~]#
```

# 参考ドキュメント
* [Kubernetes完全ガイド (impress top gear)](https://www.amazon.co.jp/dp/4295004804/)

* [Assigning Pods to Nodes (公式ドキュメント)](https://kubernetes.io/docs/concepts/configuration/assign-pod-node/#nodename)