Slide 1

Slide 1 text

がんばらないスポットインスタンス運⽤ 2020.11.11 秋のスポットインスタンス祭り ⾯⽩法⼈カヤック 藤原俊⼀郎 @fujiwara

Slide 2

Slide 2 text

@fujiwara github.com/kayac/ecspresso Amazon ECS デプロイツール github.com/fujiwara/lambroll AWS Lambda デプロイツール

Slide 3

Slide 3 text

Game & Community

Slide 4

Slide 4 text

Agenda カヤックでのスポットインスタンス活⽤の変遷 2014 〜 ⾃前⼊札期 2017 〜 Spot Fleet 期 2019 〜 Auto Scaling Group - Mixed Instance Type 期 頑張らずにスポットインスタンスを使うために

Slide 5

Slide 5 text

カヤックでのスポットインスタンス活⽤の変遷 - ⾃前⼊札期 2014年10⽉ Lobi Rec SDK リリース モバイルゲームのプレイ動画共有サービス 当初は動画変換に Amazon Elastic Transcoder を利⽤ モンスターストライクへ導⼊されてコストが問題に → EC2スポットインスタンスで変換処理

Slide 6

Slide 6 text

2014年当時のスポットインスタンス aws ec2 request-spot-instances ... ⼊札価格 台数 LaunchSpec インスタンスタイプ、Subnetなど を指定して スポットインスタンスの起動をリクエスト ⼊札価格が現在の価格より⾼ければ起動してくる リクエスト時の⼊札価格より現在の価格が⾼くなると落とされる スポット価格はオンデマンド価格より⾼くなることもある !! インスタンスを Stop できない。Terminate のみ

Slide 7

Slide 7 text

いい感じに動画変換サーバをオートスケールしたい 動画の投稿量は⼤きな波があった イベント開始直後など → EC2 コスト削減のためにオートスケールしたい

Slide 8

Slide 8 text

いい感じに動画変換サーバをオートスケールしたい 当時はスポットインスタンスをオートスケールする仕組みがなかったため ⾃前 daemon を動かして spot-request / terminate をコントロール . 動画変換queueのjobの溜まり具合を⾒る 当時はZabbixのメトリクス . 毎分jobの数を⾒て溜まっていたら台数を1.4倍にするようにspot request 5分程度何もしない cooldown time = 起動して処理が進むのを待つ . jobが減少傾向ならそれ以上起動しない . 全台の平均CPU使⽤率を⾒て、25%以上idleがあれば台数を減らしていく jobが溜まっていなくてもCPUに余裕がない 均衡している なら減らさない

Slide 9

Slide 9 text

いい感じに動画変換サーバをオ ートスケールしたい . 動画変換queueのjobの溜まり具合 を⾒る . 毎分jobの数を⾒て溜まっていたら 台数を1.4倍 . jobが減少傾向ならそれ以上起動し ない . 全台の平均CPU使⽤率を⾒て、 25%以上idleがあれば台数を減らし ていく

Slide 10

Slide 10 text

苦労した点 ⾃分ですべてやっているので、細やかな気配りが必要 インスタンスタイプ AZを固定⾼騰して起動できない → 価格をAPIを叩いて収集、安いものを優先起動 落とす時は1時間の端数を使い切りそうなものから → 当時は課⾦単位が1時間だった 今は1分 AMIをビルドするたびに追従が必要 → AMI⼀覧を取得して最新かつavailableのを使う だいぶ頑張った https://speakerdeck.com/haruyosh/amazon-ec2-auto- scaling-niyorusupotutoinsutansuhuo-yong-jiang-zuo? slide=20

Slide 11

Slide 11 text

カヤックでのスポットインスタンス活⽤の変遷 - Spot Fleet期 2015年 Spot Fleet リリース Fleet 全体のCPU数/台数を指定して、要件を満たすようスポットインスタンスを起動 → インスタンスが落ちると別インスタンスが⾃動的に起動してくる リリース当初は指定したキャパシティを保つのみ 2016年9⽉オートスケーリング対応でLobiのユースケースに適⽤可能になった → 2017年に導⼊ アプリケーションサーバコストの⼤幅削減に成功

Slide 12

Slide 12 text

アプリケーションサーバも Spot Fleet に オンデマンドのAutoScalingGroup ASG とSpotFleetを併⽤してコスト削減を試みた ASGとFleetはお互い無関係 = オートスケーリングの閾値設定がそれぞれ必要 オンデマンドはCPU 60%でスケールアウト SpotFleetはCPU 40%でスケールアウト 価格が安いSpotのほうを反応しやすくしておくとコスト効率がよい . CPU負荷が上がるとSpotが先に起動する . Spotが⾼騰して落とされる/起動できないとさらにCPU負荷が上がってくる . オンデマンドの閾値に達してオンデマンドが起動する 安価なスポットが起動できない場合には⾼価なオンデマンドでカバー

Slide 13

Slide 13 text

ASG / SpotFleet 併⽤の問題点 管理が⾯倒 例えば AMI 差し替え時… ASG : 設定変更で可能 SpotFleet : キャパシティ以外の変更は作り直し なのでこのような頑張りが必要に . 新しいAMIのFleetを作成 / 古いFleetをCancel インスタンスは⽌めない . 新しいFleetのインスタンスがELBに⼊る . ELBから古いFleetのインスタンスを外す . 古いFleetのインスタンスを削除 Fleetのキャンセル時にインスタンスを削除する設定も可能だが 120秒前の退役予告が⾶んでこないので処理中のリクエストが死ぬ

Slide 14

Slide 14 text

カヤックでのスポットインスタンス活⽤の変遷 ASG Mixed Instance Type期 2018年11⽉ ASG オンデマンド・スポットインスタンス混在対応リリース オートスケーリンググループに複数インスタンスタイプ、オンデマンド、スポットインスタン スを組み合わせて配置できるように! → SpotFleetをやめられる 2019年 Lobi で導⼊ 管理の容易さとコストの最適化を簡単に両⽴できて最⾼ 頑張らなくてよくなった!

Slide 15

Slide 15 text

安全にスポットインスタンスを使うために 頑張らなくてよいとはいえやはりオンデマンドとは違うのでいくつか考慮が必要

Slide 16

Slide 16 text

いつ落とされてもいいように備える インスタンスメタデータAPIで停⽌の120秒前に知ることが可能 ASGのライフサイクルフックでLambdaを呼ぶこともできる http://169.254.169.254/latest/meta-data/spot/instance-action {"action": "terminate", "time": "2020-09-18T08:22:00Z"} 予告が来たら速やかに停⽌準備を 例 ELB から⾃分⾃⾝を外す ログをインスタンスの外に出す ⻑時間の連続稼働が必要で、失敗できないワークロードには向かない

Slide 17

Slide 17 text

ASG Mixed Instance Type 戦略 スポットインスタンスは様々な理由で落とされることがある ASG全体のキャパシティが不⾜しないために 多様なインスタンスタイプ、AZを組み合わせる 例: c5 c5d c5n c4 m5 m5d...を 3AZに配置 配分戦略は capacity-optimized にする リアルタイムの容量データを調べ、可⽤性の最も⾼いプールを予測することで、そのプ ールからスポットインスタンスを⾃動的に起動します https://docs.aws.amazon.com/ja_jp/autoscaling/ec2/userguide/asg-purchase- options.html

Slide 18

Slide 18 text

最低台数を多めにして3AZで 例: 最低で 4xlarge * 3 で捌ける負荷だとしたら、2xlarge * 6 にする 台数が少ないと分散が⼗分ではないため、複数台同時に落ちる危険が⾼くなる 例 3台中2台が同時に落ちると突然処理能⼒が1/3に 4台が AZ a:b:c = 2:1:1 の場合、AZ-a のインスタンスが落ちると 1/2 に 3AZ構成で最低台数は3の倍数にしておくのがお勧め ASGは極⼒AZのバランスを揃えようとするため安定性が増す 1AZがすべて落ちても2/3の台数は残る

Slide 19

Slide 19 text

異世代インスタンスを混ぜて⼤丈夫? 世代が変わる C3 → C4 C4 → C5 と確実に処理は速くなるが… 実アプリケーションの処理速度はCPUだけでは決まらない CPUの速度 AZをまたぐ通信やAWS外へのリクエスト どちらも外部からみた1リクエストの処理速度 レイテンシ に影響する C5 で AZ またぎの通信が多い RDSが別AZ C4 で AZ またぎの通信が少ない RDSが同AZ 実測してみるとレイテンシは⼤差なかったりする

Slide 20

Slide 20 text

異世代インスタンスを混ぜた場合の処理能⼒平準化 ALBの最⼩未処理リクエストルーティングアルゴリズム LOR を利⽤すると 処理中のリクエストが⼀番少ないインスタンスに優先的にリクエストを回す 遅い=単位時間あたりの処理中のリクエスト数が多い 通信のレイテンシが同じであれば… CPUが遅いインスタンスにはリクエストが減る CPUが速いインスタンスにはリクエストが増える → 負荷が平準化される ただし、CPUは速いが通信のレイテンシが⼤きいインスタンスもリクエストが減る これが⼀番CPU的には暇

Slide 21

Slide 21 text

異世代インスタンスを混ぜても⼤丈夫! 我々のユースケースの場合、CPU使⽤率にして最⼤15ポイント程度の差 CPU使⽤率が 40%〜55% に分散

Slide 22

Slide 22 text

異世代インスタンスを混ぜても⼤丈夫! 平均ではなく最⼤のインスタンスのCPU負荷を⾒る ⼀番負荷の⾼いインスタンスに余裕があるうちにスケールできる閾値を決める 多少ゆるめの設定で台数が多くなっても、全台オンデマンドよりは格段に安い 安全側に倒しましょう

Slide 23

Slide 23 text

トラブル対応Tips: スポットインスタンスが全体的に枯渇したら ごくまれにある 実際にあった例: 3AZに分散していた c5.4xlarge がすべてほぼ同時に terminate → c4 を混ぜていたので致命傷にはならなかった 対応: c5d c5n m5 等を追加して影響を軽減 性能差には あまり こだわらず、多くのインスタンスタイプで分散を⼤きくする

Slide 24

Slide 24 text

トラブル対応Tips: 特定のAZでのみ起動しづらくなったら 特定AZで枯渇することがある ASGはAZ間のインスタンス台数 バランス を保つことをたいへん重視するので… . AZ-a のインスタンスが terminate . 不⾜分を補うために AZ-b c で起動する . AZ-a で起動可能になったので起動してくる . AZバランスを取るため AZ-b AZ-c のインスタンスが terminate . しかし AZ-a では枯渇気味なのですぐに terminate 2に戻る というループが始まり、ひたすら起動と停⽌を繰り返すことがある 対応: ASGのsubnetから⼀時的に枯渇しているAZのsubnetを削除してやり過ごす ELBのクロスゾーン負荷分散は有効にしておくこと

Slide 25

Slide 25 text

新機能! 2020.11.05 Capacity Rebalancing https://aws.amazon.com/jp/blogs/compute/proactively-manage-spot-instance-lifecycle- using-the-new-capacity-rebalancing-feature-for-ec2-auto-scaling/ ASG内のSpotインスタンスが中断 停⽌ 予告を受けた場合に 落ちる前に別のインスタンスを起動してくれる機能 停⽌時の⼀時的な容量減をカバーできる

Slide 26

Slide 26 text

まとめ スポットインスタンスの運⽤は、5年前は⼤変だった 昔話 ここ数年で格段に楽に。頑張らなくてよくなった! ASG Mixed Instance Type で幅広いインスタンスタイプ/AZを混ぜるのがおすすめ オートスケーリングの閾値設定は攻めすぎない