なになれ

IT系のことを記録していきます。

KubernetesでResource requestsとlimitsを最適な値にする方法

Kubernetesでは、ContainerのCPUやMemoryの使用量を設定するためのResource requestsとlimitsの機能があります。
これらの値をどのように決めるかはなかなか難しいのではないかと思います。
ただKubernetesの運用において、Resource requestsとlimitsの設定は重要です。
設定値が低すぎると実際のリソース使用量は予定以上になってしまい、リソースが不足することでPodが正常に起動しなくなる可能性があります。
設定値が高すぎると実際のリソース使用量は余裕がある状態になり、リソースの無駄が発生します。
Resource requestsとlimitsを最適な値にする必要があります。

要約

  • Vertical Pod Autoscaler(VPA)が提案する推奨値をPodのResource requestsとlimitsに設定する

概要

VPAはPodのリソース使用量を自動でスケールアップするための機能です。
ただ現時点では自動でPodのスケールアウトを行うHorizontal Pod Autoscaler(HPA)と併用ができないです。
Podのスケールアウトを利用しないのは可用性の観点からして現実的ではないので、HPAを利用しつつ、最適なリソース使用量を手動で設定するのが望ましいのではないかと思います。
VPAを実運用で利用するのではなく、最適なPodのリソース使用量を確認するためのものとして利用します。

方法

前提条件

Vertical Pod Autoscalerをインストールする

VPAのリポジトリを取得する。

$ git clone https://github.com/kubernetes/autoscaler.git

VPAをインストールする。

$ ./hack/vpa-up.sh

Goldilocksをインストールする

GoldilocksはVPAによる推奨値の確認を支援するためのツールです。

Goldilocksのリポジトリを取得する。

$ git clone https://github.com/FairwindsOps/goldilocks.git

Goldilocksをインストールする。

$ kubectl create namespace goldilocks
$ kubectl -n goldilocks apply -f hack/manifests/controller
$ kubectl -n goldilocks apply -f hack/manifests/dashboard

Goldilocksを適用するnamespaceを設定します。
ここでは、defaultのnamespaceを指定しています。

$ kubectl label ns default goldilocks.fairwinds.com/enabled=true

Resourceの推奨値を確認する

ここでは例として、Deploymentを以下のように用意します。

hamster.yaml

apiVersion: apps/v1
kind: Deployment
metadata:
  name: hamster
spec:
  selector:
    matchLabels:
      app: hamster
  replicas: 2
  template:
    metadata:
      labels:
        app: hamster
    spec:
      containers:
        - name: hamster
          image: k8s.gcr.io/ubuntu-slim:0.1
          resources:
            requests:
              cpu: 100m
              memory: 50Mi
          command: ["/bin/sh"]
          args:
            - "-c"
            - "while true; do timeout 0.5s yes >/dev/null; sleep 0.5s; done"

applyします

$ kubectl apply -f hamster.yaml

Goldilocksのダッシュボードを表示して、推奨値を確認します。

$ kubectl -n goldilocks port-forward svc/goldilocks-dashboard 8080:80
$ open http://localhost:8080/

f:id:hi1280:20200105221750p:plain:w800

Suggested Changesの欄で推奨値をコピーすることができます。

※ここでは、単にPodが動いている状態での値を推奨値としていますが、WebサービスのPod等は想定される負荷をかけて推奨値を確認する必要があると思われます

Resourceの推奨値を設定する

推奨値をdeploymentのyamlにコピペします。

hamster.yaml

apiVersion: apps/v1
kind: Deployment
metadata:
  name: hamster
spec:
  selector:
    matchLabels:
      app: hamster
  replicas: 2
  template:
    metadata:
      labels:
        app: hamster
    spec:
      containers:
        - name: hamster
          image: k8s.gcr.io/ubuntu-slim:0.1
          resources:
            limits:
              cpu: 587m
              memory: 262144k
            requests:
              cpu: 587m
              memory: 262144k
          command: ["/bin/sh"]
          args:
            - "-c"
            - "while true; do timeout 0.5s yes >/dev/null; sleep 0.5s; done"

applyします

$ kubectl apply -f hamster.yaml

ダッシュボードを確認すると値が同一になっていることが確認できます。
f:id:hi1280:20200105223419p:plain:w800

ここまでの手順でResourceの推奨値に設定することができました。

まとめ

今回の方法は実はGoldilocksというツールの利用方法をなぞっただけです。
GoldilocksというツールはResource requestsとlimitsをどのような値に設定すれば良いかという課題から生まれたツールのようです。
現状はVPAとHPAが併用できないため、Resource requestsとlimitsを手動で設定しなければならず、今回のような方法になっています。
近い将来、Kubernetesの仕組みとして自動でResourceの値が決まるようになるかもしれません。

参考

autoscaler/vertical-pod-autoscaler at master · kubernetes/autoscaler · GitHub

GitHub - FairwindsOps/goldilocks: Get your resource requests "Just Right"

Introducing Goldilocks : A Tool for Recommending Resource Requests