Cloud Intelligence™Cloud Intelligence™

Cloud Intelligence™

Container Resource MetricsでKubernetes HPAをきめ細かく制御

By Chimbu ChinnaduraiMay 2, 20244 min read

このページはEnglishDeutschEspañolFrançaisItalianoPortuguêsでもご覧いただけます。

Kubernetes Horizontal Pod Autoscaler(HPA)は、平均CPU使用率や平均メモリ使用率、あるいは任意のカスタムメトリクスをもとに、Deployment/StatefulSetのPodを需要に応じて自動でスケールアップ・スケールダウンする仕組みです。これによりworkloadsの管理は大きく変わりました。

従来の実装

Podのリソース使用量は、Pod内の各コンテナの使用量を合算した値として算出されます。しかしこの方式は、コンテナ間で使用量に強い相関がなかったり、増減のペースが揃っていなかったりするworkloadsには必ずしも適していません。

たとえば、ログを処理するサイドカーコンテナはほとんどリソースを消費しない一方で、メインのブログアプリケーションのコンテナが処理の大半を担うケースを考えてみてください。Pod全体の平均メトリクスでは実態を正しく捉えられず、HPAは本来基準にすべき重要なコンテナの使用状況に基づいたスケーリングができません。

Deployment内の全Podの平均リソース使用率に基づくHPAスケーリング

新しい実装

Kubernetes v1.20で導入され、v1.30で安定版(stable)に昇格したContainer resource metrics機能を使うと、HPAでPod内の個々のコンテナのメトリクスをターゲットに指定できます。Pod内の特定コンテナのリソース使用率(CPUやメモリなど)に基づいてスケーリングするよう、HPAを定義できるのです。

これによりリソースを効率的に割り当てられ、重要度の低いコンテナによってPod全体の使用率が押し上げられ不要なスケーリングが発生する事態も防げます。中核機能を担うコンテナのリソース消費だけを監視すれば、本来のworkloadに焦点を絞ってスケーリングを判断でき、パフォーマンスのボトルネックも未然に防げます。

Deployment内の全Podにおける、対象コンテナの平均リソース使用率に基づくHPAスケーリング

本記事では、マルチコンテナPod構成のDeploymentをスケールさせる際に、container resource metrics機能をどのように活用するかを解説します。

前提条件

  • バージョン1.27以降のKubernetesクラスター
  • KubernetesクラスターにMetrics Serverがデプロイされていること
  • 作業端末にKubectlがインストールされていること

Container resource metricsによるスケーリングを試す

  • 以下のマニフェストでサンプルとなるマルチコンテナDeploymentをデプロイします。cpu-stressorはKubernetes Pod上でCPU負荷をシミュレートするためのメインコンテナです。cpu-stressorツールの詳細はGitHubのリポジトリを参照してください。log-genertorは同じPod内に配置したサンプルのセカンダリコンテナです。

cat <<EOF | kubectl apply -f -
---
apiVersion: apps/v1
kind: Deployment
metadata:
  name: crm-scaling-demo
  labels:
    app: crm-scaling-demo
spec:
  selector:
    matchLabels:
      app: crm-scaling-demo
  template:
    metadata:
      labels:
        app: crm-scaling-demo
    spec:
      containers:
        - name: cpu-stressor
          image: narmidm/k8s-pod-cpu-stressor:1.0.0
          args:
            - "-cpu=0.5"
            - "-duration=3600s"
          resources:
            limits:
              cpu: "200m"
            requests:
              cpu: "100m"
        - name: log-generator
          image: busybox:1.28
          args: [/bin/sh, -c,\
                'i=0; while true; do echo "$i: $(date)"; i=$((i+1)); sleep 1; done']
          resources:
            requests:
              cpu: "100m"
EOF

サンプルのPodと、Pod内の全コンテナのリソース使用状況

  • Podのメトリクスではなく、cpu-stressorコンテナのCPU使用率を基準にスケーリングするHorizontailPodAutoscalerリソースを作成します。
cat <<EOF | kubectl apply -f -
---
apiVersion: autoscaling/v2
kind: HorizontalPodAutoscaler
metadata:
  name: crm-scaling-demo
spec:
  scaleTargetRef:
    apiVersion: apps/v1
    kind: Deployment
    name: crm-scaling-demo
  minReplicas: 1
  maxReplicas: 10
  metrics:
  - type: ContainerResource #new-metrics-source
    containerResource:
      name: cpu
      container: cpu-stressor #container-name
      target:
        type: Utilization
        averageUtilization: 50
EOF

cpu-stressorコンテナのメトリクスに基づくHPA設定例

この例では、HPAコントローラは、全Podのcpu-stressorコンテナにおけるCPU平均使用率が50%になるように対象をスケールさせます。

  • cpu-stressorコンテナがCPU負荷をかけ始めるのを待つと、HPAがcpu-stressorコンテナのCPU使用率に基づいてPod数を再計算する様子が確認できます。

cpu-stressorコンテナのメトリクスに基づくHPAスケーリングの例

container resource metricsを用いたHPAスケーリングのデモ

スクリーンショットとデモ動画から、マルチコンテナPod構成においてcpu-stressorコンテナを基準としたHPAスケーリングが想定どおりに動作していることがわかります🚀。

container resource metricsがKubernetes v1.30で安定版に昇格したことで、Horizontal Pod Autoscalingの精度を一段と高め、アプリケーションのパフォーマンスを最適に保てるようになりました。

本記事がお役に立てば幸いです。さらに詳しく知りたい方は、以下のリソースもあわせてご覧ください。