株式会社GxPのInternal Development Platforms室(IDP室)所属の大中です。IDP室は本年12月から新設された組織で、自分はその中で生成AIを基盤とした生産性向上を推進する…ということになっています。ですが自分のGxPで今まで行ってきたことがインフラ運用や移行作業主体だったため、RAGのようなキラキラ✨したことを推進する基盤を作る上での種々面倒くさいことを馬力で片付ける、というのが自分のロールです。
さて、今日はEC2で運用しているWebアプリケーションについて、AWSのコスト削減に取り組み、おおよそ20%程度の削減を実現した取り組みを紹介します。
まず、運用しているアプリケーションの概要は以下の通りです。
- JVMで稼働している業務アプリケーションが7つ。それぞれEC2インスタンス
- ミドルウェアのサポート条件の制約のためEC2を使用
- また、これもミドルウェアの制約で添付ファイル等のストレージはEBSを使用。ストレージ総容量はおよそ10TB
- RDBMSはRDS(PostgreSQL)。一番大きいインスタンスでデータベースのサイズは100GB程度
- アクティブユーザー4000名前後、ピーク時(平日業務開始時)に50万リクエスト/時
- AWSのインフラはTerraform+Ansibleでコード化。AMIイメージの作成にはPackerを使用
- 監視ははてな社の提供するMackerelで実施
なお、AWSアカウントの運用ポリシーの関係で、リザーブドインスタンス(RI)等のコスト削減策は使用していないため、今回これらの手法については触れません。
毎日コストチェック
この種の事例の定番ですが、Cost Explorerのレポートは毎日チェックするようにします。
このエントリーで付け加えることとしては、
- AWSのコストの集計タイミングの関係で、AWSの設定を変更したときに、それがAWSの日次コストに反映されるには2~3日かかる
- また業務システムの場合休日は課金額が落ち込むため、週の後半に設定変更の作業を行った場合は、効果が確定するまで1週間近くかかる場合がある
- 月次コストを考える時に、月の日数が30日の場合と31日の場合で3%強違い、祝日等で営業日がかわるとそちらも影響する
ということです。
未使用のリソースの削除
日常から使用していないリソースはチェックしていたはずなのですが、いざ棚卸ししてみるとNATゲートウェイ・EIP・EBSなど未使用リソースがステージング環境を中心に出てきたため、こちらは整理しました。
NATゲートウェイなどVPC関係のリソースの削除は机上での検証は十分進めた上で行いましたが、削除時にネットワーク障害を引き起こす可能性を否定できないため、運用開始後にVPC関係のリソースを作成する際は検証用であっても慎重に行う筆王があると思いました。
スナップショット・AMIの削除の定期化
リソースを整理する中で未使用のEBSを削除しましたが、EBS内のデータが削除必要と判明した場合に備えて、EBSはスナップショットを取得してから削除しました。
また、アプリケーションのアップデート時にAMIイメージごとEC2インスタンスは作り直しているため、用済みになったAMIの削除も定期作業として行うようにしました。
それからアプリケーションのアップデート時にバックアップとしてEBSはスナップショットを取得しているため、スナップショットの削除も定期作業に組みこみました。
このようなプロセスの中で出てくる課題が、スナップショットを誤って削除した時にどのようにリカバリーするのかということです。EC2では、EBSスナップショット/AMIに対して「ごみ箱」機能を有効にすることができます。ごみ箱機能を有効化すると、スナップショット/AMIを削除した際に、一定期間ごみ箱内でリソースを保持することができます。
実際運用の中でごみ箱からリソースを復旧したことがありました。スナップショットの課金はEBSを用いた運用を行っている案件では、無視できない要素です。この場合セーフガードとしてのごみ箱機能は非常に有用だと思います。
RDSのGravitonインスタンスへの切り替え
RDSのインスタンスタイプをGravitonインスタンスに変更しました。RDSをGravitonインスタンスに切り替えること自体は低コストかつ低リスクで実施できます。
ただし、当時使用していたRDSのPostgreSQLバージョンに対するサポート切れが迫っていたため、そちらを先に対応しました。当時メンテナンスウィンドウを設定しての運用をしていなかったため、インスタンスタイプの切り替えよりもバージョンアップにともなうサービス停止の調整や実際の作業に苦労したという記憶が残っています。
EC2/RDSのインスタンスタイプの変更
サービスイン後時間が経過し、使用状況が落ち着いているサービスは、EC2/RDSのインスタンスタイプを見直しました。また、最も頻繁に使用されるサービスのEC2インスタンスは、一番消費するリソースがJVMのヒープであるため、m5.4xlargeからメモリ最適化インスタンスのr7g.2xlargeに切り替えました。
EC2のGravitonインスタンスへの切り替え
EC2のインスタンスタイプをGravitonインスタンスに変更しました。CPUアーキテクチャーがaarch64に切り替わりますのでこのことへの考慮が必要です。こちらはJVMアプリケーションということがあって、それほど苦労しなかったです。
それよりもサーバーOSをこのタイミングでCentOS 7からUbuntu22.04に切り替えているのがこの作業の山場なのですが、これは別の話なので、稿を改めて話させていただきたいと思います。
RDS/EBSのストレージのGP3への切り替え
仕上げにRDS/EBSのストレージタイプをGP2からGP3に切り替えました。このことによりAWSの総コストで5%程度の削減効果をあげるこができました。
ストレージタイプの切り替えはダウンタイムなしで実施できますが、切り替え中のパフォーマンスの影響は予測しきれないところがあります。このため切り替え作業は業務時間後に実施しました。
上記のような取り組みを通じて、AWSのコストを20%程度(月で1000ドル単位)削減することができました。
コンテナベースでなくEC2ベースでのシステム運用を行っている方はそれなりの数いらっしゃると思いますので、何かの参考になればと思います。