iT邦幫忙

第 12 屆 iT 邦幫忙鐵人賽

DAY 29
0
DevOps

Docker獸 究極進化 ~~ Kubernetes獸系列 第 29

Day-29 了解 Kubernetes AutoScaler

前言

到了這個章節大家可能會開始回想,剛開始聽到K8S時很多人都說Kubernetes的AutoScaling很厲害,亦或者是Kubernetes能夠幫使用者在Cloud上省下不少錢,但Kubernetes到底是如何這到這些事情的呢?這章節我們就是來探討此事。

AutoScaling in Kubernetes

在Kubernetes cluster當中,當叢集內部觸發了某些條件時,叢集會開始所謂的AutoScaling,但是這些AutoScaling又是有分層級的,分別為:

  • HorizontalPodAutoscaler
  • VerticalPodAutoscaler
  • ClusterAutoscaler

這本篇章會透過這三種層級的Scaling來探討Kubernetes是如何辦到這件事的,以及如何觸發這件事。

What is HorizontalPodAutoScaler ?

基於CPU使用率或特定資源條件自動增減ReplicationController、ReplicaSet與Deployment中Pod的數量。特定資源條件可以為CPU、Memory、Storage或其他自訂條件。另外原本就無法自動增減的Pod是不能透過HPA進行autoScaling的,像是DaemonSet中的Pod。

HorizontalPodAutoScaler也是透過Kubernetes APi資源和控制器實現,由監控中的資源來決定控制器的行為。控制器會周期性的調整replicaSet/Deployment中Pod的數量,以使得Pod的條件資源能夠低於臨界值而不在繼續的產生新的replica。

How does HorizontalPodAutoScaler work ?

HorizontalPodAutoScaler每個週期時間會定期去查詢所監視的目標以及指定的目標資源查詢率,
來判斷目標是否需要Scaling。

https://ithelp.ithome.com.tw/upload/images/20201014/20129737cjsTiEEohC.png

Example

hpa.yaml

apiVersion: autoscaling/v1
kind: HorizontalPodAutoscaler
metadata:
  name: ironman-hpa
spec:
  scaleTargetRef:
    apiVersion: apps/v1
    kind: Deployment
    name: ironman
  minReplicas: 2
  maxReplicas: 5
  targetCPUUtilizationPercentage: 50
  • kind: HorizontalPodAutoscaler
  • spec.scaleTargetRef: 指定目標資訊
  • spec.minReplicas: 指定目標最小數目的Replicas
  • spec.MaxReplicas: 指定目標能scaling的最大replica數
  • targetCPUUtilizationPercentage: 指定目標的Scaling條件,這邊為CPU的平均百分比。

Algorithm details

desiredReplicas = ceil[currentReplicas * ( currentMetricValue / desiredMetricValue )]

  1. 假設當前metric value為200m,但target metric value為100m,這時比較值為200 / 100 == 2.0 ,需要兩倍的replicas
  2. 假設當前metric value為50m,但target metric value為100m,這時比較值為50 / 100 == 0.5,只需要一半replicas
  3. 假設當前metric value為92m,但target metric value為100m,這時比較值為92 / 100 == 0.92,因為1.00 - 0.92 = 0.08 小於預設容忍值0.1,因此放棄此次的scaling。

What is VerticalPodAutoscaler ?

VerticalPodAutoscaler有兩個目標:

  1. 通過自動配置資源請求來減少運維成本。
  2. 在提高集群資源利用率的同時最小化容器出現內存溢出或CPU 飢餓的風險。

也因此VerticalPodAutoscaler透過幾個方法達成該目標:

  • VPA 能夠在Pod 提交時設置容器的資源(CPU和內存的請求和限制)。
  • VPA 能夠配置在資源上的固定限制,特別是最小和最大資源請求。
  • VPA能夠調整已存在的Pod 的容器資源,特別是能夠對CPU 飢餓和內存溢出等事件作出響應。
  • VPA能與Pod控制器兼容(deployment)。

How does VerticalPodAutoscaler work ?

VerticalPodAutoscaler,它包括一個標籤識別器label selector(匹配Pod)、資源策略resources policy(控制VPA如何計算資源)、更新策略update policy(控制資源變化應用到Pod)和推薦資源信息。

並且VPA能夠透過VPA Controller做到以下幾件事:

  • 監控所有該類型Pod,並持續地為每個Pod計算新的推薦資源,並儲存至VPA Object當中。
  • 提供一個同步API來獲取所有Pod資訊,並返回給Pod推薦訊息。
  • 所有的Pod創建請求都會通過VPA Admission Controller。如果Pod與任何一個VPA對象匹配,那麼Admission controller會依據VPARecommender推薦的值重寫容器的資源。如果Recommender連接不上,它將會返回VPA Object中緩存的推薦信息。
  • 透過History storage紀錄Pod歷史資源使用相關資訊,Recommender在一開始用這些歷史數據來初始化狀態。History Storage基礎的實現是使用Prometheus。

https://ithelp.ithome.com.tw/upload/images/20201014/20129737HRbHkYUf9O.png

Example

deployment.yaml

apiVersion: apps/v1
kind: Deployment
metadata:
  name: ironman
  labels:
    name: ironman
    app: ironman
spec:
  minReadySeconds: 5
  strategy:
    type: RollingUpdate
    rollingUpdate:
      maxSurge: 1
      maxUnavailable: 1
  selector:
    matchLabels:
      app: ironman
  replicas: 1
  template:
    metadata:
      labels:
        app: ironman
    spec:
      containers:
       - name: ironman
         image: ghjjhg567/ironman:latest
         imagePullPolicy: Always
         ports:
           - containerPort: 8100
         resources:
           limits:
             cpu: "1"
             memory: "2Gi"
           requests:
             cpu: 500m
             memory: 256Mi
         envFrom:
           - secretRef:
               name: ironman-config
         command: ["./docker-entrypoint.sh"]
       - name: redis
         image: redis:4.0
         imagePullPolicy: Always
         ports:
           - containerPort: 6379
       - name: nginx
         image: nginx
         imagePullPolicy: Always
         ports:
           - containerPort: 80
         volumeMounts:
           - mountPath: /etc/nginx/nginx.conf
             name: nginx-conf-volume
             subPath: nginx.conf
             readOnly: true
           - mountPath: /etc/nginx/conf.d/default.conf
             subPath: default.conf
             name: nginx-route-volume
             readOnly: true
           - mountPath: "/var/www/html"
             name: mypd
         readinessProbe:
           httpGet:
             path: /v1/hc
             port: 80
           initialDelaySeconds: 5
           periodSeconds: 10
      volumes:
        - name: nginx-conf-volume
          configMap:
            name: nginx-config
        - name: nginx-route-volume
          configMap:
            name: nginx-route-volume
        - name: mypd
          persistentVolumeClaim:
            claimName: pvc
  • spec.spec.containers.resources: VPA相關資訊,Pod提交時,透過VPA去設定該Pod的資源設置。

What is ClusterAutoscaler ?

Cluster層級的Scaler,當物件因資源不足而無法生成啟動時,或者是叢集節點使用率過低時,ClusterAutoScaler會自動地去調節節點的數量。

How to use ClusterAutoscaler ?

這邊以GCP為例

Creating a cluster with autoscaler

$ gcloud container clusters create cluster-name --num-nodes 30 \
    --enable-autoscaling --min-nodes 15 --max-nodes 50 [--zone compute-zone]
  • —num-nodes: 結點創建初始值,預設為3。
  • --enable-autoscaling: 啟動autoscaler與否。
  • --min-nodes: node pool中最低的節點數。
  • --max-nodes: node pool中最高的節點數。

Adding a node pool with autoscaling

$ gcloud container node-pools create pool-name --cluster cluster-name \
    --enable-autoscaling --min-nodes 1 --max-nodes 5 [--zone compute-zone]
  • —cluster: 叢集名稱

Enabling autoscaling for an existing node pool

$ gcloud container clusters update cluster-name --enable-autoscaling \
    --min-nodes 1 --max-nodes 10 --zone compute-zone --node-pool default-pool

Disabling autoscaling for an existing node pool

$ gcloud container clusters update cluster-name --no-enable-autoscaling \
    --node-pool pool-name [--zone compute-zone --project project-id]

後記

今天我們暸解了Kubernetes cluster在三種不同的層面分別使用的資源縮放策略,這也讓我們在往後遇到不同的問題,能透過最為合適的方法去進行資源調配,節省資源的浪費。

https://ithelp.ithome.com.tw/upload/images/20201014/20129737xEUhaGhRSR.png

Reference

https://www.servicemesher.com/blog/kubernetes-vertical-pod-autoscaler/

https://kubernetes.io/docs/tasks/run-application/horizontal-pod-autoscale/

https://cloud.google.com/kubernetes-engine/docs/concepts/verticalpodautoscaler

https://cloud.google.com/kubernetes-engine/docs/how-to/cluster-autoscaler?hl=zh-tw


上一篇
Day-28 暸解 Namespace 與 Rbac
下一篇
Day-30 學習 Helm (上)
系列文
Docker獸 究極進化 ~~ Kubernetes獸30

尚未有邦友留言

立即登入留言