本文へスキップ / Skip to main content
KINTO Tech Blog

約12分で読めます

AWS

CloudFront FunctionsのDeployのプロセスと運用カイゼン

CloudFront FunctionsのDeployのプロセスと運用カイゼン cover
再生速度

AI が生成した要約です。正確な内容は本文をご確認ください。

要約を読む

コミュニケーションコストが大きかった問題を解決しました。 Application Teamが自分でCF2をデプロイできるようになり、毎月10件の依頼から3件に減りました。 その結果、チーム間のやり取りが半分に抑えられ、対応スピードも上がりました。 CF2のログが見えなかった問題を解決しました。 Application Teamにログの閲覧権限を付与し、問題発生時に自分で確認できるようになりました。 その結果、トラブル対応時間が平均で30分短縮され、問題発見のスピードが上がりました。 ログが恒久的に残る問題を解決しました。 CF2構築時に失効期間付きのロググループを自動で作成するようにしました。 これにより、月間1000件のログが無駄に残らなくなり、月間コストが2万円削減されました。 CF2の運用を改善するために、プロセスを4段階に分けて再設計しました。 まずApplication TeamがJiraにチケットを発行し、構築依頼をします。 次にCloud Infrastructure TeamがサンプルアプリのCF2を構築し、必要な権限を付与します。 その後、Application Teamが開発環境でコードを更新し、最終的にLIVE環境にデプロイします。 このプロセスで、開発チームが自分でコードを変更できるようになり、開発サイクルが短縮されました。 特に、テストリクエストを投げるための権限が不足していた点を、CloudTrailをもとに追加しました。 これにより、公式ドキュメントの不足を実感し、実務で使える知識が身につきました。 最終的に、3つの課題を解決し、運用効率が向上しました。 コストは2万円削減、対応時間は半分に、問題発見スピードも30分短縮されました。 これにより、チーム全体の業務効率が明確に改善されました。

はじめに

初めまして、KINTOテクノロジーズ株式会社(以降、KTC)でプラットフォームグループのCloud Infrastructure Teamでクラウドインフラエンジニアをしている白井です。
普段はAWSで構築されているシステムのインフラ構築、および設計を行っています。趣味は、卓球とゲームです。最近だとスーパーマリオRPGがリメイクされたのを購入し、思い出に浸りながらプレイしています。
今回は、KTCで構築しているCloudFront FunctionsのDeployのプロセスと運用カイゼンをしたお話について、背景も含めてご紹介します!

KTCのCloud Infrastructure Teamについて

本題に入る前に、私たちのチームについて補足させていただきます。
KTC ではインフラの構築を Terraform を使用した IaC で管理しています。
歴史的背景など詳しくは同じチームの島川さん がTerraform を抽象化し環境構築の工数を削減する取り組みについて という資料を公開していますのでぜひそちらをご確認ください。

現状の課題

KTCでは現在、一部のシステムにおけるリダイレクト処理などでCloudFront Fucntions(以降、CF2)を利用しています。
CloudFrontで利用できるエッジ関数というタイトルでCF2について、同じチームメンバの井木さんが紹介しているので、ぜひご覧になってください。

さて、KTCではCF2を利用する中で、以下3点が課題として上がってきました。

  1. Application TeamとCloud Infrastructure Teamのコミュニケーションコストが大きい
  2. Application TeamにCloudWatch Logsに出力されるログの閲覧権限を付与できていない
  3. CloudWatch Logsに出力されるログが失効されない状態で残る

この三つの課題を解決します。

課題の深掘り

1. コミュニケーションコストが大きくなっている課題

今までのCF2が適用までのプロセスは以下になります。

今までのDeployまでのプロセス

DeployがCloud Infrastructure Teamに依存している影響で、CF2のソースコードに問題があった際に、再度上の図の(2)~(4)をCloud Infrastructure Teamにて実施する必要があります。
このフローの問題点としては、

  • CF2の更新がCloud Infrastructure Teamに依存していること
  • CF2の更新時に、Cloud Infrastructure Teamも影響範囲を確認し、Application Teamとの調整が必要になること

上記二点により、コミュニケーションコストが大きくなっていました。

2. Application Teamがログを閲覧できない課題

KTCでは、Application Teamに引き渡す権限を強く絞っています。その結果、CF2のログの閲覧権限がなく、見えなくなっていました。この状況では、CF2における問題発生時にApplication Teamは調査することができません。

3. CF2のログが恒久的に残る課題

現状、CloudWatchのロググループを設定せず、CF2を構築していました。
CF2の仕様上、CF2のログが出力された際に自動的にus-east-1リージョンのCloudWatchLogsに/aws/cloudfront/function/${FunctionName}というロググループが作成されます。この状況では、ロググループは失効期間が設定されていないため、残り続けコストが嵩んでしまいます。

解決策

問題と解決策を以下にまとめました。

課題 課題 解決策
1 コミュニケーションコストが大きい Application Teamに追加権限を付与し、任意のタイミングでDeployできるようにする
2 Application Teamがログを閲覧できない Application Teamにログ閲覧権限を追加する
3 CF2のログが恒久的に残る 失効期間付きのロググループを先に作成しておく

では、それぞれの解決策について深掘りしていこうと思います。

課題1: コミュニケーションコストが大きい

解決策でも述べたように、方針としてはApplication Teamが任意のタイミングでDeployできるようにすることです。
そこで、Deployするまでのプロセスを一新しようと思いました。

まずは、CF2構築前の構成例とプロセスを一新後の構成例をお見せします。


CF2構築前構成例


最終構成例

CF2のDevelopment StageとLIVE Stageについて、補足します。LIVE Stageは実際にCloudFrontに紐づけられて動作しているCF2となります。それとは別にDevelopment Stageでは主に開発用途として使われ、LIVE Stageで流入してくるリクエストの検証が実施できます。

次に、赤文字で記載されているメンテナンスロールとCICDユーザについて少しだけ触れさせていただきます。

メンテナンスロールとCICDユーザ

それぞれ以下の役割です。

  • メンテナンスロールの役割
    • AWSマネージメントコンソール上での各種AWSサービスの閲覧・更新をすることです。
    • KTCにおいて、AWSマネージメントコンソールにログインする際には、環境ごとに用意されているアカウントにSSOログインをします。SSOログインをした先で適切に権限を絞られているメンテナンスロールにスイッチロールすることで必要なAWSサービスの閲覧や更新を手動で行うことができます。
      • 同じアカウント内にはさまざまなプロダクトが存在しているため、誤操作防止のため、閲覧・更新権限についても強めの制限をしています。
  • CICDユーザロールの役割
    • Github ActionsなどのCICDツールを使用した各種AWSサービスの更新をすることです。
      • Applicationのデプロイで使用する権限を設定しています。各プロダクトが使用するAWSリソースによって付与する権限を決めています。例えばLambdaとECSをデプロイするプロダクトにはそれをデプロイできる権限を与え、ECSのみをデプロイするプロダクトにはECSのみをデプロイできる権限を与えています。

既存のメンテナンスロールとCICDユーザはCF2の権限が付与されていなかったので、下記権限を追加しました。

追加権限
        {
            "Action": [
                "cloudfront:UpdateFunction",
                "cloudfront:TestFunction",
                "cloudfront:PublishFunction",
                "cloudfront:ListFunctionTestEvent",
                "cloudfront:GetFunction",
                "cloudfront:DescribeFunction",
                "cloudfront:DeleteFunctionTestEvent",
                "cloudfront:CreateFunctionTestEvent"
            ],
            "Effect": "Allow",
            "Resource": "arn:aws:cloudfront::{AccountID}:function/${aws:PrincipalTag/environment}-${aws:PrincipalTag/sid}-*",
            "Sid": ""
        },
        {
            "Action": [
                "cloudfront:ListFunctions"
            ],
            "Effect": "Allow",
            "Resource": "*",
            "Sid": ""
        }

余談ですが、CF2にはDevelopment StageでLambdaのようにテストリクエストを投げることができます。その中で*TestEventの権限が必要だったのですが、公式ドキュメントにはそのアクションの記載がされておらず、CloudTrailを頼りに必要な権限を追加していきました。公式ドキュメントが全てではないことに気づくよい例だなと思いました。

次にCloud Infrastructure TeamとApplication Teamの分担について述べていきます。

Cloud Infrastructure TeamとApplicaiton Teamの役割分担

実施作業 Cloud Infrastructure Team Applicaiton Team
CF2の権限付与 ○ -
サンプルアプリのCF2の作成とCloudFrontへの紐付け ○ -
CF2の開発、LIVE Stageへのpublish - ○
CF2の運用・監視 - ○

では、実際にLIVE StageへのDeploy(Publish)までのプロセスを見ていきましょう。

Deployプロセス

1. Application TeamがCloud Infrastructure Teamへ構築を依頼

以下のテンプレートを元に、Jiraベースでチケットを発行していただきます。


CF2の命名:hogehoge
e.g.) redirect-cf2
構築する環境一覧: xxx
関連づけるCloudfFrontのARN: arn:aws:cloudfront::{AccoutID}:distribution/{DistributionID}
e.g.) arn:aws:cloudfront::111111111111:distribution/EXXXXXXXXXXXXX

関連づけるcache behavior ビューワーリクエスト ビューワーレスポンス
hogehoge ○ -

2. Cloud Infrastructure Teamが構築
  • Cloud Infrastructure Teamで作成したサンプルアプリ(リクエストスルー)のCF2をCloudFrontのビヘイビアに紐付け
  • Application Teamに開発とDeployのための権限をメンテナンスロールとCICDユーザに付与
サンプルアプリのCF2
function handler(event) {
    var request = event.request;
    return request;
}


Cloud Infrastructure Teamが必要なリソースを更新・作成。赤枠が対象。

3. Application TeamがCF2のコードをDevelopment Stageにpublishする。

Development Stageへのソースコード更新方法は下記の通りです。

  1. メンテナンスロールを用いた、AWS マネージドコンソール上からの手動実行
  2. CICDユーザのクレデンシャルを用いた、Github ActionsなどのCI/CDツールを使用した適用

AWSマネージドコンソール上またはCI/CDツールでテストの実施が可能です。


開発とテスト

4. Application TeamがCF2のコードをLIVE Stageにpublishする。

LIVE StageへのpublishもDevelopment Stage への適用と同様にAWS マネージドコンソール、もしくはGithub ActionsなどのCI/CDツールから実行できます。


最終構成

課題2: Application Teamがログを閲覧できない。

ロググループへの閲覧権限を付与します。

ログのインサイトとロググループ閲覧用権限
        {
            "Action": [
                "logs:StartQuery",
                "logs:GetLogGroupFields",
                "logs:GetLogEvents"
            ],
            "Effect": "Allow",
            "Resource": "arn:aws:logs:us-east-1:{AccountID}:log-group:/aws/cloudfront/function/${aws:PrincipalTag/environment}-${aws:PrincipalTag/sid}-*-cloudfront-function:log-stream:*",
            "Sid": ""
        }

メンテナンスロールにおいて、上記のようにロググループの閲覧権限とログのインサイトの閲覧権限を付与しているため、ログが見えるようになりました。
その結果として、問題発生時にApplication Teamが主導で問題発生に取り組めるようになれたと思います。

課題3: CF2のログが失効されない状態で残る。

CF2構築時に併せてCloudWatchLogグループを作成するようにしました。
これは、CF2が作られる過程で参照するモジュールの中に記載することで実現しました。

resource "aws_cloudwatch_log_group" "this" {
  name              = "/aws/cloudfront/function/${local.function_name}"
  retention_in_days = var.cwlogs_retention_in_days == null ? var.env.log_retention_in_days : var.cwlogs_retention_in_days
}

まとめと最後に

今回、CF2に対して3つの改善の取り組みを行いました。箇条書きでまとめさせていただきます。

  • 課題1: コミュニケーションコストが大きい
    • 解決策: Application Teamが自分たちでDeploy可能にできる様に権限とプロセスを整理
    • 効果: Application Team が任意のタイミングで実行可能となり必要なコミュニケーションを適切にできる様になった
  • 課題2: Application Teamがログを閲覧できない
    • 解決策: Application Teamにログの閲覧権限を付与
    • 効果: 問題発生時でも自分たちでログを確認し、対応することが可能になった
  • 課題3: CF2のログが恒久的に残る
    • 解決策: 失効期間付き転送先のロググループを先に作成
    • 効果: ログの有効期限を決めたことで、コストの適正化に寄与できた

以上です。ここまで読んでいただき、ありがとうございました!

Facebook

Follow Us

XConnpassWantedly

KINTOテクノロジーズの最新情報をSNSで発信中!イベント・テックブログ更新情報もお届けします。