【セッションレポート】Amazon EKS + Karpenter で始めるスケーラブルな基盤作り(AWS-36) #AWSSummit

2024.06.21

はじめに

お疲れさまです。とーちです。

現在開催中のAWS Summit 2024で行われた「Amazon EKS + Karpenter で始めるスケーラブルな基盤作り」のレポートをお伝えします。

セッション視聴

セッションはオンデマンドで視聴可能です。公開期限は2024年7月5日(金)までとなっておりますので、視聴される場合はお早めにアクセスしてください。

セッション概要

セッション概要 タイトル : Amazon EKS + Karpenter で始めるスケーラブルな基盤作り

本セッションでは、Amazon EKS の運用を検討しているお客様、Amazon EKS + Cluster Autoscaler を運用中のお客様に対して、Kubernetes のNodeライフサイクルマネージャーである Karpenter の魅力をお伝えします。加えて、Cluster Autoscaler から Karpenter への移行方法をご紹介します。

スピーカー : 祖父江 宏祐

セッションレベル : 300

レポート内容

対象者とゴール

  • 対象者
    • k8s,EKSの知識を有し、EKS基盤を構築しようとしている人
    • すでにEKSを運用していてスケラービリティに課題を感じている
  • セッションゴール
    • Karpenterの概要の理解
    • Karpenterを動かす具体的なイメージができる

EKSのスケーリング

  • EKSの基盤をスケーラブルにするためにはどのようなリソースを使えばいいか
    • 1つ目はPod
      • Podの負荷が高まるとサービスが適切に提供できないのでPodの数を増やす
      • Podの数がどんどん増えるとNodeのリソースがいっぱいになる
    • Nodeのスケーリングを意識する必要がある
      • NodeのリソースがいっぱいのときPodを立ち上げようとするとペンディング状態になるので、Nodeを増やす必要がある
    • Podの数に従い、Nodeが適切に増減するとスケーラブルといえる

Karpenterによる課題の解決

  • 従来はNodeのスケーリングにはCluster Autoscalerを使っていた
    • AWSではAutoScalingGroupにNodeグループがマッピング
    • Cluster AutoscalerではPodを意識したスケーリングではなくAutoScalingGroupのロジックに従っている
    • この結果リソースが足りずに起動できなかったり、大きすぎるNodeを用意することがある
      • そのためNodeグループの属性(vCPU,Memory、AZなど)を揃えることが推奨されている
    • Nodeグループを複数組み合わせて使っているユーザが多い
    • 管理者はどのようにNodeグループを作成するとコストなどを最適化できるかに頭を悩ませることになる
    • 具体例
      • クラスタ管理者は作成するNodeグループ設計のためにヒアリングした
        • 開発チームAは64GBのPodのメモリを割り当てたい
        • 開発チームBは小さめのNodeで良いとのこと
          • 開発チームA用のNodeグループで賄えるがコスト最適化できてない
        • 開発チームCはARMのインスタンスを使いたい
          • Gravitonを起動するための別のNodeグループが必要
      • この要望を実現すると9つのNodeグループを作成する必要が出てくる
        • 要件が増えればさらにNodeグループが増える
    • 理想としては開発チームからの要望が増えても設定数が増えづらく、かつ、コスト最適化が出来ている状況が理想
      • これの満たす方法の一つがKarpenter
    • KarpenterはAWSが作成したCluster AutoScaler
      • KarpenterははNodeグループを使わない
      • 効率的な運用、コスト最適化、可用性の維持がKarpenterの特徴
  • Cluster AutoScalerとKarpenterのスケーリング動作の違い
    • Cluster AutoScaler
      • ペンディングのPodが発生するとCluster AutoScalerが検知してAutoScalingGroupと連携してEC2を追加
    • Karpenter
      • ペンディングになったPodをKarpenterが検知、EC2フリートのAPIをコールすることでEC2追加
      • NodeグループではなくNodeに対して直接スケーリングをかけるのが特徴
      • このため、複数のNodeグループを用意しておく必要がない
      • KarpenterではNodeプールという概念でNodeのグループを用意するがNodeの属性を完全一致で設定する必要はない
    • Karpenterが起動するNodeはNodeプールの要件に一致してPodの要件にあう最低価格のNodeを起動する動きとなる
      • この結果、設定数が増えづらくコスト最適な状態が作りやすい
    • EKSをプロダクションで利用する際にはNodeを起動するだけでは不十分なケースがある
      • 具体例
        • ラベルがついたNodeを起動したい
          • KarpenterではラベルがついたNodeも起動できる
        • 3AZにPodを分散して配置したい
          • k8sではtopologyspreadconstraintsという設定があり、Karpenterはそれを考慮してNodeを起動できる
        • スポットインスタンスを起動したい
          • Karpenterではスポットインスタンスも起動できる、price capacity optimized戦略でNodeを起動する
          • ただしスポットインスタンスを含めるとスポットインスタンスを優先的に起動しようとするので注意
          • Karpenterは起動するNodeに様々なラベルを付与する。購入オプションのラベルも含まれる
            • オンデマンドのラベルがついたNodeにのみPodを起動といった設定が可能
    • Karpenterを使ったスケールイン
      • Podが動いていないNodeをKarpenterが削除可能と判断すると、Nodeを削除する
      • Podが利用するリソースに対してNodeのリソースが過剰な場合、新たなNodeに置き換える
      • これらをconsolidationと呼ぶ
      • Karpenterはスポットインスタンスも扱える、スポットインスタンスを扱う上で大事なのは中断イベントをキャッチして適切に処理すること
        • KarpenterではSQSでイベントを受け取れる。
      • スポットインスタンスはデフォルトではconsolidationの対象ではないので注意
    • 長時間ジョブを実行するというワークロードでは、consolidationにジョブ実行Podが巻き込まれることがある
      • KarpenterはPodに付与されたアノテーションを考慮して動くことができる
      • この結果、ジョブ実行Podをconsolidationの対象外にすることができる
  • Karpenterの設定
    • Nodeプール
      • Karpenterが作成可能なNodeの条件
    • EC2Nodeクラス
      • Nodeプールが起動するEC2の設定
      • この設定に従いNodeの追加、削除をする
  • Nodeプールの設定
    • Karpenterはyamlで設定を行う
    • 以下の設定項目がある
      • CPUアーキテクチャ
      • OS
      • EC2購入オプション
      • インスタンスファミリー(c,m,rなど)
    • And条件になるので、すべての条件にマッチするNodeを起動しようとする
  • EC2Nodeクラス
    • 以下の設定項目がある
      • AMIの種類
      • Nodeが属するサブネット
        • tag、id
      • EC2にアタッチするセキュリティグループ
        • tag,id ,name

Demo

  • Demoで行うこと
    • 3Azに分散してPodを動かす
    • 開発チームAは64GBのPod一つ
    • 開発チームBは小さめのPodを60個、3AZに分散
  • スケールアウトとスケールインに注目
    • Nodeプールの設定はk8sのマニフェストとして登録されている
  • 実際のDemoの様子
    • まず開発チームBのPodを実行。60個すべてのPodがペンディング状態になった
    • 30秒程度でNodeが稼働し始めた
    • 開発チームAのPodの起動
    • Karpenterは64GBのメモリがないので、新たなNodeを追加した
    • Karpenterはクラスタのコスト効率を高めるためにNodeの入れ替えを実施
    • c6a.4xlargeを削除してr6aのインスタンスで動かし始めた
      • $3.4/hourが最終的に$2.6/hourくらいまで削減

移行方法

  • Cluster AutoscalerからKarpenterへの移行方法
    • Karpenter用とNode用のIAMロールを作成する
    • AWSリソースに対してタグ付けをする
      • サブネット
      • SG
    • Karpenterの設定作成
      • Nodeプール
      • EC2Nodeクラス
    • EC2のイベント取得用リソース
      • SQS
      • Eventbridge
  • Karpenterのデプロイ、IAMロールのアタッチを実施
  • Karpenterが管理するNodeにKarpenterPodを配置するのは非推奨
    • KarpenterPodはCluster Autoscaler上に配置
  • KarpenterとCluster Autoscalerが同居する期間は両方がスケーリングするので注意する

感想

EKSはほんとに少ししか触ったことがなかったので、Nodeのスケーリングの部分は知識がなかったのですが、このセッションを聞くことでそこを補完できました。 Karpenterの主要な設計ポイントがわかったので、スムーズにKarpenterを使い始められそうです。 また、Nodeが立ち上がりの速さは素晴らしいと思いました。スケーリング速度が重視されるような状況でぜひ使ってみたいです。