GKEクラスタのサイズアップ方法

# GKEクラスタのサイズアップ方法
クラスタのリソースが枯渇してきた場合に、クラスタのサイズをアップする2種類の方法があるので、それぞれの手順をまとめる。

- Nodeスケールアウト方式
- Nodeスケールアップ方式

# Nodeスケールアウト方式
Nodeの数を増やすことで、クラスタのサイズをアップすることができる。
既存Nodeのリソースが足りない場合、新たに作成したNodeにPodの作成がスケジューリングされる。

## クラスタのサイズ変更
https://cloud.google.com/kubernetes-engine/docs/how-to/resizing-a-cluster?hl=ja

```
gcloud container clusters resize {cluster-name} --num-nodes 2
```

## Nodeに紐づく永続ディスクについて
https://cloud.google.com/kubernetes-engine/docs/how-to/persistent-volumes/readonlymany-disks?hl=ja
> 複数のノードで同時に書き込みモードの永続ディスクを接続することはできません。

上記のページに書いてあるとおり、複数のNode間で同時に書き込みモードの永続ディスクを接続させることはできないので
既存Nodeに紐づく永続ディスクのアクセスモードにReadWriteOnceを設定している場合、
このNodeスケールアウト方式ではサイズアップできない。

また、ボリュームを多数のNodeで読み書き可能としてマウントするReadWriteManyはアクセスモードとしてGCEのディスクを使用するPersistentVolumeでは、使用できない。
よって、書き込み可能なディスクを紐付けている場合、Nodeスケールアウト方式でクラスタのサイズアップをすることはできない。

複数のNodeで書き込み可能なストレージを利用したい場合は、
以下の記事を参考にGKE上にNFSを構築し永続ストレージとすれば
Nodeスケールアウト方式でサイズアップができる。
https://qiita.com/devs_hd/items/dbcafb54f6789280036a

結論として、
書き込み可能なGCEディスクを紐付けている場合は、Nodeスケールアップ方式に記載した手順で、Nodeのマシンスペックをアップするしかない。
Nodeスケールアウト方式にしたければ、NSFを構築しストレージとする。

# Nodeスケールアップ方式
既存の単一Nodeのマシンタイプを変更し、スペックアップすることで。クラスタのサイズアップができる。
上述だが、書き込み可能なGCE永続ディスクを既存Nodeに接続している場合、選択肢はこちらしかない。

## Nodeのマシンタイプの変更方法
基本的には公式ドキュメントのとおりコマンドを叩いていくだけでいい。

 **公式ドキュメント** 
https://cloud.google.com/kubernetes-engine/docs/tutorials/migrating-node-pool?hl=ja
 **参考Qiita** 
https://qiita.com/yagince/items/9d66a6cf58b2905c16db

```
# 新しいマシンタイプのnode-poolを作成する
gcloud container node-pools create larger-pool \
  --cluster={cluster-name} \
  --machine-type=n1-standard-2 \
  --num-nodes=1

# 既存のnode-poolにPodがスケジュールされるのを止める
for node in $(kubectl get nodes -l cloud.google.com/gke-nodepool=default-pool -o=name); do
  kubectl cordon "$node";
done

# 既存のnode-poolで実行されているPodをドレイン
# ※ドレインすると既存NodeからPodが排出されるため、再スケジュールされるのだが、このとき新しいnode-poolにスケジュールされる
for node in $(kubectl get nodes -l cloud.google.com/gke-nodepool=default-pool -o=name); do
  kubectl drain --force --ignore-daemonsets --delete-local-data --grace-period=10 "$node";
done

# 既存のnode-poolを削除する
gcloud container node-pools delete default-pool --cluster {cluster-name}
```

## Nodeに紐づく永続ディスクについて
https://cloud.google.com/kubernetes-engine/docs/concepts/persistent-volumes?hl=ja

> PersistentVolumeClaim は、リクエストを満たす PersistentVolume が存在する場合やプロビジョニング可能な場合、PersistentVolumeClaim はその PersistentVolume にバインドされます。
> クラスタは要求を検査してバインドされたボリュームを検出し、そのボリュームをポッドにマウントします。

要するにPodのボリュームにPersistentVolumeClaimを指定している場合、
Podを新たなNodeに移動するだけで永続ディスクの紐付けも完了する。
既存Nodeが削除された時点で、書き込み可能モードの永続ディスクの接続が開放され新たなNodeでマウントできるようになるので、永続ディスクの紐付けをし直す、などの作業は要らない。
 **PersistentVolumeClaimを削除してしまうと、対応するPersistentVolumeオブジェクトとプロビジョニングされたCompute Engineの永続ディスクも削除されてしまうため、動的プロビジョニングでディスクを作成した場合、PersistentVolumeClaimの削除は絶対に行ってはいけない。** 

PersistentVolumeClaimを削除しても永続ディスクが削除されないようにするには、以下の設定をする。
> 動的にプロビジョニングされた永続ディスクが削除されないようにするには、PersistentVolume リソースまたはその StorageClass リソースの再利用ポリシーを Retain に設定します。この場合、PersistentVolumeClaim を使用していなくても、永続ディスクが存在する限り永続ディスクの料金が発生します。

事情があり、永続ディスクを動的に紐付けるのではなく、既存の永続ディスクをPersistentVolumeとして使用したい場合は、以下のページを参考に作業する。
https://cloud.google.com/kubernetes-engine/docs/how-to/persistent-volumes/preexisting-pd?hl=ja