LinuCエヴァンジェリストの鯨井貴博@opensourcetechです。
はじめに
今回は、kubernetesのDeploymentの耐障害性(自動復旧)とオートスケーリングを検証してみます。
なお、kubernetesは以下の記事で作成したクラスターを使っています。
DualStack(IPv4 & IPv6)のkubernetesクラスター構築(v1.26.00・ubuntu22.04)
https://www.opensourcetech.tokyo/entry/20230314/1678782139
検証すること
検証する内容は、以下の通りです。
・Deploymentの耐障害性(自動復旧)
→ Deploymentで起動されるPodがダウンした際の挙動確認
・オートスケーリング
→ スケールアウト(Pod数の増加)する際の挙動確認
→スケールイン(Pod数の減少)する際の挙動確認
Deploymentの耐障害性(自動復旧)
ではまず、Deploymentの耐障害性(自動復旧) からやってみます。
なお、使用するService(type:LoadBalancer)は以下の記事で作成したMetalLBが必要になるので予め用意する、もしくはNodePortを使うようにしてください。
MetalLBとService(type:LoadBalancer)による外部クライアントへのサービス公開(kubernetes v1.26.00 on ubuntu22.04)
では、DeploymentとServiceのデプロイ。
kubeuser@master01:~/autoscaling$ ls deployment.yaml hpa.yaml kubeuser@master01:~/autoscaling$ cat deployment.yaml apiVersion: apps/v1 kind: Deployment metadata: name: hpa-nginx spec: replicas: 4 selector: matchLabels: run: hpa-nginx template: metadata: labels: run: hpa-nginx spec: containers: - name: hpa-nginx image: nginx:latest ports: - containerPort: 80 resources: limits: cpu: 100m requests: cpu: 50m --- apiVersion: v1 kind: Service metadata: name: hpa-nginx labels: run: hpa-nginx spec: ports: - port: 80 selector: run: hpa-nginx type: LoadBalancer kubeuser@master01:~/autoscaling$ kubectl apply -f deployment.yaml --dry-run=client deployment.apps/hpa-nginx created (dry run) service/hpa-nginx created (dry run) kubeuser@master01:~/autoscaling$ kubectl apply -f deployment.yaml deployment.apps/hpa-nginx created service/hpa-nginx created kubeuser@master01:~/autoscaling$ kubectl get deployments,pods NAME READY UP-TO-DATE AVAILABLE AGE deployment.apps/hpa-nginx 4/4 4 4 42s deployment.apps/nginx 2/2 2 2 12d deployment.apps/nginx2 1/1 1 1 12d NAME READY STATUS RESTARTS AGE pod/hpa-nginx-668b69fd79-9qqpb 1/1 Running 0 41s pod/hpa-nginx-668b69fd79-k7d2q 1/1 Running 0 41s pod/hpa-nginx-668b69fd79-pzxdl 1/1 Running 0 41s pod/hpa-nginx-668b69fd79-v5bjk 1/1 Running 0 41s pod/nginx-6cbc9bb4f5-jm8mr 1/1 Running 0 12d pod/nginx-6cbc9bb4f5-pfhfz 1/1 Running 0 12d pod/nginx2-f96cfc57b-vnsfm 1/1 Running 0 12d pod/webserver-master01 1/1 Running 0 9d kubeuser@master01:~/autoscaling$ kubectl get svc NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE hpa-nginx LoadBalancer 10.1.114.112 192.168.1.53 80:31842/TCP 68s kubernetes ClusterIP 10.1.0.1 <none> 443/TCP 21d nginx LoadBalancer 10.1.55.116 192.168.1.51 80:30267/TCP 12d
hpa-nginxという名前のDeployment・Pod(4つ)・Serviceが作成されました。
では、続いて耐障害性の確認ということで、
Podを手動で削除すると自動復旧するか確認してみます。
kubeuser@master01:~/autoscaling$ kubectl get pods -w NAME READY STATUS RESTARTS AGE hpa-nginx-668b69fd79-9qqpb 1/1 Running 0 4m9s hpa-nginx-668b69fd79-k7d2q 1/1 Running 0 4m9s hpa-nginx-668b69fd79-pzxdl 1/1 Running 0 4m9s hpa-nginx-668b69fd79-v5bjk 1/1 Running 0 4m9s . . . kubectl delete pods hpa-nginx-668b69fd79-9qqpb --forceでPodを強制的に削除 ※別のターミナルで実施しています . . . hpa-nginx-668b69fd79-9qqpb 1/1 Terminating 0 4m45s hpa-nginx-668b69fd79-9qqpb 1/1 Terminating 0 4m45s hpa-nginx-668b69fd79-xnqfx 0/1 Pending 0 0s hpa-nginx-668b69fd79-xnqfx 0/1 Pending 0 0s hpa-nginx-668b69fd79-xnqfx 0/1 ContainerCreating 0 1s hpa-nginx-668b69fd79-xnqfx 0/1 ContainerCreating 0 4s hpa-nginx-668b69fd79-xnqfx 1/1 Running 0 8s
Pod(hpa-nginx-668b69fd79-9qqpb)を強制的に削除したあと、代わりのPod(hpa-nginx-668b69fd79-xnqfx)が起動され自動復旧しています。
オートスケーリング
続いてオートスケーリングの検証です。
大量のHTTPリクエストを投げつけて、負荷が増加するにつれPodが増加、
負荷が減少するにつれPodが減少するか確認します。
※負荷は、Apache Benchを使ってかけます。
まずオートスケーリングするためのリソース(HorizontalPodAutoscaler)をデプロイします。
※CPU負荷によって、Podが最大10までスケールアウトされる
kubeuser@master01:~/autoscaling$ ls deployment.yaml hpa.yaml kubeuser@master01:~/autoscaling$ cat hpa.yaml apiVersion: autoscaling/v2 kind: HorizontalPodAutoscaler metadata: name: hpa-nginx spec: scaleTargetRef: apiVersion: apps/v1 kind: Deployment name: hpa-nginx minReplicas: 1 maxReplicas: 10 metrics: - type: Resource resource: name: cpu target: type: Utilization averageUtilization: 50 kubeuser@master01:~/autoscaling$ kubectl apply -f hpa.yaml --dry-run=client horizontalpodautoscaler.autoscaling/hpa-nginx created (dry run) kubeuser@master01:~/autoscaling$ kubectl apply -f hpa.yaml horizontalpodautoscaler.autoscaling/hpa-nginx created kubeuser@master01:~/autoscaling$ kubectl get hpa NAME REFERENCE TARGETS MINPODS MAXPODS REPLICAS AGE hpa-nginx Deployment/hpa-nginx <unknown>/50% 1 10 0 6s kubeuser@master01:~/autoscaling$ kubectl get hpa NAME REFERENCE TARGETS MINPODS MAXPODS REPLICAS AGE hpa-nginx Deployment/hpa-nginx 0%/50% 1 10 4 37s
まだ負荷をかけていない(アクセスがない状態)なので、スケールアウト/スケールインの基準となるCPU使用率は0%となっています。
では、Apache Benchによる負荷をかけていきましょう。
c:\xampp\apache\bin>ab.exe -n 100000 -c 100 http://192.168.1.53/ This is ApacheBench, Version 2.3 <$Revision: 1901567 $> Copyright 1996 Adam Twiss, Zeus Technology Ltd, http://www.zeustech.net/ Licensed to The Apache Software Foundation, http://www.apache.org/ Benchmarking 192.168.1.53 (be patient) Completed 10000 requests Completed 20000 requests Completed 30000 requests Completed 40000 requests Completed 50000 requests Completed 60000 requests Completed 70000 requests Completed 80000 requests Completed 90000 requests Completed 100000 requests Finished 100000 requests Server Software: nginx/1.23.4 Server Hostname: 192.168.1.53 Server Port: 80 Document Path: / Document Length: 615 bytes Concurrency Level: 100 Time taken for tests: 379.038 seconds Complete requests: 100000 Failed requests: 0 Total transferred: 84800000 bytes HTML transferred: 61500000 bytes Requests per second: 263.83 [#/sec] (mean) Time per request: 379.038 [ms] (mean) Time per request: 3.790 [ms] (mean, across all concurrent requests) Transfer rate: 218.48 [Kbytes/sec] received Connection Times (ms) min mean[+/-sd] median max Connect: 0 3 19.1 0 1024 Processing: 9 375 202.8 334 3403 Waiting: 0 240 187.5 225 2387 Total: 12 379 204.0 339 3404 Percentage of the requests served within a certain time (ms) 50% 339 66% 357 75% 367 80% 378 90% 423 95% 472 98% 1343 99% 1390 100% 3404 (longest request)
上記Apache Benchによるアクセスによって、Podの数が増加します。
kubeuser@master01:~/autoscaling$ kubectl get hpa -w NAME REFERENCE TARGETS MINPODS MAXPODS REPLICAS AGE hpa-nginx Deployment/hpa-nginx 0%/50% 1 10 4 2m36s hpa-nginx Deployment/hpa-nginx 34%/50% 1 10 4 3m15s hpa-nginx Deployment/hpa-nginx 75%/50% 1 10 4 3m31s hpa-nginx Deployment/hpa-nginx 68%/50% 1 10 6 3m46s hpa-nginx Deployment/hpa-nginx 54%/50% 1 10 6 4m1s hpa-nginx Deployment/hpa-nginx 30%/50% 1 10 6 4m16s hpa-nginx Deployment/hpa-nginx 34%/50% 1 10 6 4m31s hpa-nginx Deployment/hpa-nginx 50%/50% 1 10 6 4m46s hpa-nginx Deployment/hpa-nginx 42%/50% 1 10 6 5m16s hpa-nginx Deployment/hpa-nginx 38%/50% 1 10 6 5m31s hpa-nginx Deployment/hpa-nginx 47%/50% 1 10 6 5m46s hpa-nginx Deployment/hpa-nginx 63%/50% 1 10 6 6m1s hpa-nginx Deployment/hpa-nginx 36%/50% 1 10 8 6m16s hpa-nginx Deployment/hpa-nginx 39%/50% 1 10 8 6m31s hpa-nginx Deployment/hpa-nginx 29%/50% 1 10 8 6m47s hpa-nginx Deployment/hpa-nginx 28%/50% 1 10 8 7m2s hpa-nginx Deployment/hpa-nginx 35%/50% 1 10 8 7m17s hpa-nginx Deployment/hpa-nginx 32%/50% 1 10 8 7m32s hpa-nginx Deployment/hpa-nginx 37%/50% 1 10 8 7m47s hpa-nginx Deployment/hpa-nginx 29%/50% 1 10 8 8m2s hpa-nginx Deployment/hpa-nginx 28%/50% 1 10 8 8m17s hpa-nginx Deployment/hpa-nginx 39%/50% 1 10 8 8m32s hpa-nginx Deployment/hpa-nginx 26%/50% 1 10 8 8m47s hpa-nginx Deployment/hpa-nginx 32%/50% 1 10 8 9m2s hpa-nginx Deployment/hpa-nginx 28%/50% 1 10 8 9m17s hpa-nginx Deployment/hpa-nginx 12%/50% 1 10 8 9m32s hpa-nginx Deployment/hpa-nginx 0%/50% 1 10 8 9m48s
kubeuser@master01:~$ kubectl get pods -w NAME READY STATUS RESTARTS AGE hpa-nginx-668b69fd79-k7d2q 1/1 Running 0 17m hpa-nginx-668b69fd79-pzxdl 1/1 Running 0 17m hpa-nginx-668b69fd79-v5bjk 1/1 Running 0 17m hpa-nginx-668b69fd79-xnqfx 1/1 Running 0 12m nginx-6cbc9bb4f5-jm8mr 1/1 Running 0 12d nginx-6cbc9bb4f5-pfhfz 1/1 Running 0 12d nginx2-f96cfc57b-vnsfm 1/1 Running 0 12d webserver-master01 1/1 Running 0 9d hpa-nginx-668b69fd79-4cb2g 0/1 Pending 0 0s hpa-nginx-668b69fd79-4cb2g 0/1 Pending 0 0s hpa-nginx-668b69fd79-fjxg2 0/1 Pending 0 0s hpa-nginx-668b69fd79-4cb2g 0/1 ContainerCreating 0 0s hpa-nginx-668b69fd79-fjxg2 0/1 Pending 0 0s hpa-nginx-668b69fd79-fjxg2 0/1 ContainerCreating 0 0s hpa-nginx-668b69fd79-4cb2g 0/1 ContainerCreating 0 2s hpa-nginx-668b69fd79-fjxg2 0/1 ContainerCreating 0 2s hpa-nginx-668b69fd79-fjxg2 1/1 Running 0 5s hpa-nginx-668b69fd79-4cb2g 1/1 Running 0 6s hpa-nginx-668b69fd79-gmbcn 0/1 Pending 0 0s hpa-nginx-668b69fd79-dwt7h 0/1 Pending 0 0s hpa-nginx-668b69fd79-gmbcn 0/1 Pending 0 0s hpa-nginx-668b69fd79-dwt7h 0/1 Pending 0 0s hpa-nginx-668b69fd79-gmbcn 0/1 ContainerCreating 0 0s hpa-nginx-668b69fd79-dwt7h 0/1 ContainerCreating 0 0s hpa-nginx-668b69fd79-gmbcn 0/1 ContainerCreating 0 1s hpa-nginx-668b69fd79-dwt7h 0/1 ContainerCreating 0 2s hpa-nginx-668b69fd79-gmbcn 1/1 Running 0 5s hpa-nginx-668b69fd79-dwt7h 1/1 Running 0 6s
最終的には8Podまで増加しました。
続いて、アクセスがなくなりPodが減少していく様子をみてみましょう。
kubeuser@master01:~/autoscaling$ kubectl get hpa -w NAME REFERENCE TARGETS MINPODS MAXPODS REPLICAS AGE . . . hpa-nginx Deployment/hpa-nginx 0%/50% 1 10 7 11m hpa-nginx Deployment/hpa-nginx 0%/50% 1 10 7 13m hpa-nginx Deployment/hpa-nginx 0%/50% 1 10 6 13m hpa-nginx Deployment/hpa-nginx 0%/50% 1 10 6 14m hpa-nginx Deployment/hpa-nginx 0%/50% 1 10 5 14m hpa-nginx Deployment/hpa-nginx 0%/50% 1 10 2 14m hpa-nginx Deployment/hpa-nginx 0%/50% 1 10 1 14m
kubeuser@master01:~$ kubectl get pods -w . . . hpa-nginx-668b69fd79-gmbcn 1/1 Terminating 0 5m16s hpa-nginx-668b69fd79-gmbcn 1/1 Terminating 0 5m17s hpa-nginx-668b69fd79-gmbcn 0/1 Terminating 0 5m19s hpa-nginx-668b69fd79-gmbcn 0/1 Terminating 0 5m19s hpa-nginx-668b69fd79-gmbcn 0/1 Terminating 0 5m19s hpa-nginx-668b69fd79-dwt7h 1/1 Terminating 0 7m32s hpa-nginx-668b69fd79-dwt7h 1/1 Terminating 0 7m32s hpa-nginx-668b69fd79-dwt7h 0/1 Terminating 0 7m33s hpa-nginx-668b69fd79-dwt7h 0/1 Terminating 0 7m34s hpa-nginx-668b69fd79-dwt7h 0/1 Terminating 0 7m34s hpa-nginx-668b69fd79-4cb2g 1/1 Terminating 0 10m hpa-nginx-668b69fd79-4cb2g 1/1 Terminating 0 10m hpa-nginx-668b69fd79-4cb2g 0/1 Terminating 0 10m hpa-nginx-668b69fd79-4cb2g 0/1 Terminating 0 10m hpa-nginx-668b69fd79-4cb2g 0/1 Terminating 0 10m hpa-nginx-668b69fd79-pzxdl 1/1 Terminating 0 28m hpa-nginx-668b69fd79-fjxg2 1/1 Terminating 0 10m hpa-nginx-668b69fd79-v5bjk 1/1 Terminating 0 28m hpa-nginx-668b69fd79-pzxdl 1/1 Terminating 0 28m hpa-nginx-668b69fd79-v5bjk 1/1 Terminating 0 28m hpa-nginx-668b69fd79-fjxg2 1/1 Terminating 0 10m hpa-nginx-668b69fd79-pzxdl 0/1 Terminating 0 28m hpa-nginx-668b69fd79-pzxdl 0/1 Terminating 0 28m hpa-nginx-668b69fd79-pzxdl 0/1 Terminating 0 28m hpa-nginx-668b69fd79-fjxg2 0/1 Terminating 0 10m hpa-nginx-668b69fd79-fjxg2 0/1 Terminating 0 10m hpa-nginx-668b69fd79-fjxg2 0/1 Terminating 0 10m hpa-nginx-668b69fd79-v5bjk 0/1 Terminating 0 28m hpa-nginx-668b69fd79-v5bjk 0/1 Terminating 0 28m hpa-nginx-668b69fd79-v5bjk 0/1 Terminating 0 28m hpa-nginx-668b69fd79-xnqfx 1/1 Terminating 0 24m hpa-nginx-668b69fd79-xnqfx 1/1 Terminating 0 24m hpa-nginx-668b69fd79-xnqfx 0/1 Terminating 0 24m hpa-nginx-668b69fd79-xnqfx 0/1 Terminating 0 24m hpa-nginx-668b69fd79-xnqfx 0/1 Terminating 0 24m
最終的には、HorizontalPodAutoscalerリソースで定義した最小Pod数1まで減少しました。
おわりに
今回Deploymentの耐障害性(自動復旧)とオートスケーリング(スケールアウト/スケールイン)を試してみましたが、挙動としてはイメージ通りでした。
しかしやってみなければ分からなかった細かい挙動の違いを確認することができました。
具体的には、以下。
・Pod数の変化:Deploymentで定義した4つ → CPU負荷増加で8つ → CPU負荷減少で1つ
・どのようなタイミングでPodの増減が起こるのか
増加はすぐ、減少は数分(3分程度で始まり6分程度で収束完了)かかる
・Podの数は、HorizontalPodAutoscalerリソースで定義した最大Pod数/最大Pod数の間で制御される
・HorizontalPodAutoscalerリソースは、定義したCPU使用率(閾値)を超えたらPodを増やし、閾値内に収まる(or 最大Pod数に達する)までPodを増加させる
※以下のログで様子が分かりますね!
kubeuser@master01:~/autoscaling$ kubectl get hpa -w NAME REFERENCE TARGETS MINPODS MAXPODS REPLICAS AGE hpa-nginx Deployment/hpa-nginx 0%/50% 1 10 4 2m36s hpa-nginx Deployment/hpa-nginx 34%/50% 1 10 4 3m15s hpa-nginx Deployment/hpa-nginx 75%/50% 1 10 4 3m31s hpa-nginx Deployment/hpa-nginx 68%/50% 1 10 6 3m46s hpa-nginx Deployment/hpa-nginx 54%/50% 1 10 6 4m1s hpa-nginx Deployment/hpa-nginx 30%/50% 1 10 6 4m16s hpa-nginx Deployment/hpa-nginx 34%/50% 1 10 6 4m31s hpa-nginx Deployment/hpa-nginx 50%/50% 1 10 6 4m46s hpa-nginx Deployment/hpa-nginx 42%/50% 1 10 6 5m16s hpa-nginx Deployment/hpa-nginx 38%/50% 1 10 6 5m31s hpa-nginx Deployment/hpa-nginx 47%/50% 1 10 6 5m46s hpa-nginx Deployment/hpa-nginx 63%/50% 1 10 6 6m1s hpa-nginx Deployment/hpa-nginx 36%/50% 1 10 8 6m16s
改めて、実際にやってみることの大事さを知った検証でした。