AKS で負荷に応じて Pod の数を変更する / 手動・自動スケールアウト

今回は AKS で負荷に応じたスケールアウトをする方法を見ていきます。この記事は前回までの環境を前提としています。
前回記事 -> https://qiita.com/komiyasa/items/a1afb4b0c244990047a1

#Kubernetes のスケーラビリティ
Kubernetes はスケーラビリティが長所のひとつです。システムの稼働状況や負荷にあわせてシステムを拡張できます。システムの拡張方法は、スケールアウト、スケールアップの二つの種類がります。

- スケールアウト
スケールアウトは、水平スケールといわれるように、システムを構成するサーバーの台数そのものを増やす方法です。何らかの原因でサーバーが一台ダウンしても、別のサーバーで処理することができるため、システムの可用性を高めることが可能です。

- スケールアップ
スケールアップは、垂直スケールともいわれるように、サーバーの台数を増やすのではなく、サーバーの CPU 、メモリ、ディスク容量などのコンピューティングリソースを増やす方法です。

この二つをしっかりを分けて理解しておくことで、必要に応じた適切なスケーラビリティを確保することが出来ます。今回は、スケールアウトの方法についてみていきたいと思います。

#Pod を手動水平スケールする
ここでは Pod の数を手動でスケールしていきます。まずは下記マニフェストファイルを使って、3つの Pod を動かす ReplicaSet を定義し作成します。※前回記事で見てきたものと近しいです。

```podscalesample.yaml
apiVersion: apps/v1
kind: ReplicaSet
metadata:
  name: nginx-replicaset

spec:
  replicas: 3
  selector:
    matchLabels:
      app: photo-view

  template:
    metadata:
      labels:
        app: photo-view
        
    spec:
      containers:
      - image: nginx
        name: photoview-container
```

`kubectl apply -f podscalesample.yaml` コマンドを Azure CLI から実行し Pod を作成します。そのあとで `kubectl get pod` を実行し、Pod の Status を確認します。3つの Pod が Running の状態にあることが分かります。

```
$ kubectl get pod
NAME                     READY   STATUS    RESTARTS   AGE
nginx-replicaset-lmsmh   1/1     Running   0          16s
nginx-replicaset-vwmhl   1/1     Running   0          16s
nginx-replicaset-w256q   1/1     Running   0          16s
```

次に、`kubectl scale` コマンドを使用して、Pod の数を増やします。例えば 8 つに増やしたいときは、`kubectl scale --replicas=8 rs/nginx-replicaset` を実行します。

```
$ kubectl scale --replicas=8 rs/nginx-replicaset
replicaset.extensions/nginx-replicaset scaled
```

再び `kubectl get pods` コマンドで確認すると、新しく 5 つの Pod が作成されているのが分かります。

```
$ kubectl get pod
NAME                     READY   STATUS    RESTARTS   AGE
nginx-replicaset-f5c5v   1/1     Running   0          47s
nginx-replicaset-lmsmh   1/1     Running   0          3m40s
nginx-replicaset-sqd5t   1/1     Running   0          47s
nginx-replicaset-t4ngr   1/1     Running   0          47s
nginx-replicaset-vwmhl   1/1     Running   0          3m40s
nginx-replicaset-w256q   1/1     Running   0          3m40s
nginx-replicaset-wm9lm   1/1     Running   0          47s
nginx-replicaset-zdt8n   1/1     Running   0          47s
```
これで手動で Pod をスケールできることが確認できました。ここまで出来たらいったん `delete` コマンドで Pod を削除しておきましょう。

#Pod を自動水平スケールする
まずは以下のマニフェストファイルを使用して、二つの Pod をもつ ReplicaSet を作成します。

```replicasetsample.yaml
apiVersion: apps/v1
kind: ReplicaSet
metadata:
  name: busy-replicaset

spec:
  replicas: 2 
  selector:
    matchLabels:
      app: busy
      
  template:
    metadata:
      labels:
        app: busy
    spec:
      containers:
      - image: busybox   
        name: hpa-container
        command: ["dd", "if=/dev/zero", "of=/dev/null"]
        resources:
          requests:  
            cpu: 100m
          limits:
            cpu: 100m
```

これで 2 つの Pod が作成されました。次は自動スケールするためのマニフェストファイルを作成します。

```autoscale.yaml
apiVersion: autoscaling/v2beta1
kind: HorizontalPodAutoscaler
metadata:
  name: budy-hpa

spec:
  minReplicas: 1   # レプリカ数の最大
  maxReplicas: 5   # レプリカ数の最小

  metrics:
  - resource:
      name: cpu
      targetAverageUtilization: 30
    type: Resource
  
  #  スケールするReplicaSetの設定
  scaleTargetRef:
    apiVersion: apps/v1
    kind: ReplicaSet
    name: busy-replicaset
```

上記のマニフェストファイルの、`spec:minReplicas` の部分でレプリカ数の最小、`spec:maxReplicas` の部分でレプリカ数の最大を定義します。その下の `metrics` の部分でスケールする条件を定めますここでは CPU の Utilization が 30 % になるように定義しています。このマニフェストファイルを `kubeclt apply -f autoscale.yaml` を実行して適用します。

```
$ kubectl apply -f autoscale.yaml
horizontalpodautoscaler.autoscaling/budy-hpa created
```

これで、`kubectl get hpa -w` を実行してみます。 -w コマンドはループ処理を実行し、状況が変わったら自動的に更新するオプションです。初めに実行すると以下のような結果を返します。

```
$ kubectl get hpa -w
NAME       REFERENCE                    TARGETS    MINPODS   MAXPODS   REPLICAS   AGE
budy-hpa   ReplicaSet/busy-replicaset   100%/30%   1         5         5          86s
```

しばらくすると(1分くらい)、Pod が自動的に増えています。

```
$ kubectl get pod
NAME                    READY   STATUS    RESTARTS   AGE
busy-replicaset-5cv2r   1/1     Running   0          2m42s
busy-replicaset-c8p8g   1/1     Running   0          2m42s
busy-replicaset-fx72v   1/1     Running   0          10m
busy-replicaset-hwpdr   1/1     Running   0          10m
busy-replicaset-j6xmm   1/1     Running   0          2m27s
```

これは 100% 使用されている状況だったので、HPA で定めた Pod の上限値の範囲内で Pod を自動スケールした結果です。このようにマニフェストファイルで定義してあげるだけで、負荷に応じて Pod の数を自動でスケーリングすることが可能となりました。

#参考URL
Horizontal Pod Autoscaler
https://kubernetes.io/docs/tasks/run-application/horizontal-pod-autoscale/