メインコンテンツにスキップ

SAMでLambdaのCloudWatch Logs保存期間を設定

タグ: 🏷 AWS ,Lambda ,SAM ,CloudWatch Logs

はじめに

AWS Lambda関数を開発・運用していると、実行ログがCloudWatch Logsに自動的に保存されます。これはデバッグやモニタリングに非常に便利ですが、デフォルト設定のままではログが無期限に保存され続けるため、意図せずストレージコストが増加してしまう可能性があります。

この問題を解決するため、ログの保存期間を適切に設定することが重要です。本記事では、AWS SAM (Serverless Application Model) を利用して、Lambda関数のログ保存期間をコードで管理する方法を具体的に解説します。

なぜログの保存期間を設定するのか?

  • コスト削減: CloudWatch Logsの料金は、収集(取り込み)と保存(ストレージ)の2つの要素で決まります。不要になったログを自動的に削除することで、ストレージコストを大幅に削減できます。
  • コンプライアンス要件: プロジェクトや組織のポリシーによっては、ログの保持期間が定められている場合があります。コードで設定することで、要件を確実に満たすことができます。
  • 運用効率の向上: 手動で各ロググループの保存期間を設定するのは手間がかかり、設定漏れのリスクもあります。SAMテンプレートで一元管理することで、効率的かつ確実に設定を適用できます。

SAMテンプレートでの設定方法

AWS SAMは、AWS::Serverless::Function リソースを定義すると、CloudFormationへの変換時に対応する AWS::Logs::LogGroup リソースを自動的に生成します。このロググループの論理IDは、[FunctionLogicalId]LogGroup という命名規則になっています。

この仕組みを利用し、SAMテンプレート内で同じ論理IDを持つ AWS::Logs::LogGroup リソースを明示的に定義することで、自動生成されるリソースのプロパティを上書きできます。

具体的なテンプレート例

以下は、MyLambdaFunction という論理IDのLambda関数に対して、ログの保存期間を14日に設定する template.yaml の例です。

AWSTemplateFormatVersion: '2010-09-09'
Transform: AWS::Serverless-2016-10-31
Description: An example of setting log retention for a Lambda function.

Resources:
  # Lambda関数の定義
  MyLambdaFunction:
    Type: AWS::Serverless::Function
    Properties:
      FunctionName: my-awesome-function
      CodeUri: src/
      Handler: app.lambda_handler
      Runtime: python3.9

  # Lambda関数に対応するロググループを明示的に定義
  MyLambdaFunctionLogGroup:
    Type: AWS::Logs::LogGroup
    Properties:
      # ロググループ名は !Sub を使って動的に生成します
      # /aws/lambda/<関数名> という形式です
      LogGroupName: !Sub "/aws/lambda/${MyLambdaFunction}"
      # ここでログの保存期間を指定します
      RetentionInDays: 14

解説

  • MyLambdaFunctionLogGroup: これがロググループを定義するリソースです。論理IDはLambda関数の論理ID MyLambdaFunctionLogGroup を付けたものと一致させる必要があります。
  • LogGroupName: !Sub "/aws/lambda/${MyLambdaFunction}" を使用して、SAMが生成するLambda関数の物理名(この場合は my-awesome-function)からロググループ名を動的に構築します。これにより、関数名とロググループ名が正しく紐づきます。
  • RetentionInDays: このプロパティでログの保存日数を指定します。

RetentionInDays に設定可能な値

RetentionInDays には、以下のいずれかの値を設定できます。

  • 1, 3, 5, 7
  • 14
  • 30
  • 60
  • 90
  • 120
  • 150
  • 180
  • 365
  • 400
  • 545
  • 731
  • 1827
  • 3653

プロジェクトの要件に応じて、適切な日数を選択してください。指定しない(またはリソースを定義しない)場合は、デフォルトの「永続 (Never Expire)」になります。

注意点:既存のロググループがある場合

すでにLambda関数をデプロイ・実行しており、対応するロググループがCloudWatch Logsに存在している状況でこのテンプレートを適用しようとすると、sam deploy が失敗することがあります。

これは、CloudFormationが MyLambdaFunctionLogGroup リソースを新規に作成しようとした際に、同名のロググループ(/aws/lambda/my-awesome-function など)がすでに存在するために発生するエラーです。

解決策

この問題を解決するには、sam deploy を実行する前に、既存のCloudWatch Logsロググループを手動で削除する必要があります。

  1. AWSマネジメントコンソールでCloudWatchのサービスページを開きます。
  2. ナビゲーションペインから「ロググループ」を選択します。
  3. 該当するロググループ(例: /aws/lambda/my-awesome-function)を検索して選択し、削除します。

ロググループを削除しても、Lambda関数自体には影響ありません。次回の sam deploy 実行時に、CloudFormationによって正しい保存期間が設定された新しいロググループが作成されます。