AWS Secrets Manager におけるローテーションのトラブルシューティング - AWS Secrets Manager

AWS Secrets Manager におけるローテーションのトラブルシューティング

多くのサービスでは、Secrets Manager は、Lambda 関数を使用してシークレットをローテーションします。詳しくは、「Lambda 関数によるローテーション」を参照してください。Lambda ローテーション関数は、シークレットの対象となるデータベースまたはサービス、および Secrets Manager とやり取りします。ローテーションが想定通りに動作していないときは、まず CloudWatch Logs を確認します。

注記

一部のサービスは、ユーザーのためにシークレットを管理できます (自動ローテーションの管理など)。詳しくは、「AWS Secrets Manager シークレットのマネージドローテーション」を参照してください。

AWS Lambda 関数のシークレットローテーションの失敗をトラブルシューティングする方法

Lambda 関数でシークレットローテーションが失敗した場合は、次の手順を使用して問題のトラブルシューティングと解決を行います。

考えられる原因

  • Lambda 関数の同時実行が不十分である

  • ローテーション中の複数の API コールによる競合状態

  • Lambda 関数ロジックが正しくない

  • Lambda 関数とデータベース間のネットワークの問題

一般的なトラブルシューティングステップ

  1. CloudWatch ログを分析します:

    • Lambda 関数ログで特定のエラーメッセージまたは予期しない動作を検索する

    • すべてのローテーションステップ (CreateSecretSetSecretTestSecretFinishSecret) が試行されていることを確認する

  2. ローテーション中に API コールを確認します:

    • Lambda ローテーション中にシークレットで API コールが変更されないようにする

    • RotateSecretPutSecretValue の呼び出しの間に競合状態がないことを確認する

  3. Lambda 関数ロジックを確認します:

    • シークレットローテーションに最新の AWS サンプルコードを使用していることを確認する

    • カスタムコードを使用する場合は、すべてのローテーションステップが適切に処理されることを確認する

  4. ネットワーク構成を確認します:

    • セキュリティグループルールで Lambda 関数がデータベースにアクセスできることを確認する

    • Secrets Manager の適切な VPC エンドポイントまたはパブリックエンドポイントアクセスを確保する

  5. シークレットバージョンをテストします:

    • シークレットの AWSCURRENT バージョンがデータベースアクセスを許可していることを確認する

    • AWSPREVIOUS または AWSPENDING のバージョンが有効かどうかを確認する

  6. 保留中のローテーションをクリアします:

    • ローテーションが一貫して失敗する場合は、AWSPENDING ステージングラベルをクリアしてローテーションを再試行する

  7. Lambda の同時実行設定を確認します:

    • 同時実行設定がワークロードに適していることを確認する

    • 同時実行の問題が疑われる場合は、「同時実行関連のローテーション失敗のトラブルシューティング」に関するセクションを参照する

「環境変数に認証情報が見つかりました」の後にアクティビティがない

「環境変数に認証情報が見つかりました」の後にアクティビティがなく、タスクの所要時間が長い (例: デフォルトの Lambda タイムアウトは 30000 ms) 場合は、Secrets Manager エンドポイントへのアクセス時に Lambda 関数がタイムアウトしている可能性があります。

ローテーション用の Lambda 関数は、Secrets Manager のエンドポイントにアクセスできる必要があります。Lambda 関数がインターネットにアクセスできる場合は、パブリックなエンドポイントを使用できます。エンドポイントを見つけるには、「AWS Secrets Manager のエンドポイント」を参照してください。

インターネットにアクセスできない VPC で Lambda 関数を実行する場合は、Secrets Manager サービスのプライベートなエンドポイントを、VPC 内に設定することをお勧めします。VPC は、リージョンのパブリックなエンドポイントに向けられたリクエストを傍受し、それらをプライベートエンドポイントにリダイレクトします。(詳しくは、「VPC エンドポイント (AWS PrivateLink)」を参照してください。)

別の方法としては、NAT ゲートウェイまたはインターネットゲートウェイを VPC に追加して (これで VPC のトラフィックはパブリックエンドポイントに到達できます)、Lambda 関数から Secrets Manager のパブリックなエンドポイントへのアクセスを許可することも考えられます。この方法では、VPC がある程度のリスクにさらされることになります。ゲートウェイ向けの IP アドレスには、パブリックなインターネットから攻撃が可能なためです。

「CreateSecret」の後にアクティビティがない

CreateSecret の実行後にローテーションが停止する原因となる問題は次のとおりです。

VPC ネットワーク ACL では、HTTPS トラフィックの送受信が許可されません。

詳細については、「Amazon VPC ユーザーガイド」の「ネットワーク ACL を使用してサブネットへのトラフィックを制御する」を参照してください。

Lambda 関数のタイムアウト設定が短すぎてタスクを実行できません。

詳細については、「AWS Lambda デベロッパーガイド」の「Lambda 関数オプションの設定」を参照してください。

Secrets Manager VPC エンドポイントは、割り当てられたセキュリティグループへの進入時に VPC CIDR を許可しません。

詳細については、「Amazon VPC ユーザーガイド」の「セキュリティグループを使用してリソースへのトラフィックを制御する」を参照してください。

Secrets Manager VPC エンドポイントポリシーでは、Lambda が VPC エンドポイントを使用することを許可していません。

(詳しくは、「AWS Secrets Manager VPC エンドポイントの使用」を参照してください。)

シークレットは交代ユーザーローテーションを使用し、スーパーユーザーシークレットは Amazon RDS によって管理され、Lambda 関数は RDS API にアクセスできません。

スーパーユーザーシークレットが他の AWS サービスによって管理されている交代ユーザーローテーションでは、Lambda ローテーション関数がサービスエンドポイントを呼び出してデータベース接続情報を取得できる必要があります。データベースサービスに VPC エンドポイントを設定することを推奨します。詳細については、以下を参照してください。

エラー:「KMS へのアクセスは許可されていません」

ClientError: An error occurred (AccessDeniedException) when calling the GetSecretValue operation: Access to KMS is not allowed が表示されている場合、シークレットの暗号化に使用された KMS キーを使用してシークレットを復号化するアクセス許可が、ローテーション関数に付与されていません。暗号化コンテキストを特定のシークレットに制限する条件が、アクセス許可ポリシーに含まれている可能性があります。必要なアクセス許可の詳細については、「カスタマーマネージドキーのポリシーステートメント」を参照してください。

エラー: 「シークレット JSON にキーがありません」

Lambda ローテーション関数では、シークレット値が特定の JSON 構造になっている必要があります。このエラーが表示される場合は、ローテーション関数がアクセスしようとしたキーが JSON にない可能性があります。各タイプのシークレットの JSON 構造については、「AWS Secrets Manager シークレットの JSON 構造 」を参照してください。

エラー: 「setSecret: データベースにログインできません」

このエラーを引き起こす可能性のある問題は次のとおりです。

ローテーション関数はデータベースにアクセスできません。

タスクの所要時間が長い (例: 5000 ミリ秒以上) 場合、Lambda ローテーション関数はネットワーク経由でデータベースにアクセスできない可能性があります。

データベースまたはサービスを VPC の Amazon EC2 インスタンスで実行している場合は、同じ VPC で Lambda 関数を設定することをお勧めします。こうすることで、ローテーション関数はサービスと直接通信できるようになります。詳細については、Configuring VPC access を参照してください。

Lambda 関数からデータベースまたはサービスへのアクセスを可能にするには、ローテーション用の Lambda 関数にアタッチされたセキュリティグループによって、そのデータベースまたはサービスに対するアウトバウンド接続が許可されている必要があります。同時に、データベースまたはサービスにアタッチされているセキュリティグループでは、ローテーション用 Lambda 関数からのインバウンド接続を許可する必要もあります。

シークレットの認証情報が正しくありません。

タスクの所要時間が短い場合、Lambda ローテーション関数がシークレット内の認証情報を使用しても認証できない可能性があります。AWS CLIのコマンド get-secret-valueAWSCURRENTAWSPREVIOUS のバージョンのシークレットの情報を使用し、手動でログインして認証情報を確認します。

データベースは scram-sha-256 を使用してパスワードを暗号化します。

Aurora PostgreSQL バージョン 13 以降のデータベースで、パスワードの暗号化に scram-sha-256 を使用しているが、ローテーション関数が scram-sha-256 をサポートしていない libpq バージョン 9 以前を使用している場合、ローテーション関数はデータベースに接続できません。

scram-sha-256 暗号化を使用するデータベースユーザーを判別するには
  • ブログ「SCRAM Authentication in RDS for PostgreSQL 13」(RDS for PostgreSQL 13 での SCRAM 認証) の「Checking for users with non-SCRAM passwords」(SCRAM 以外のパスワードを持つユーザーの確認) を参照してください。

ローテーション関数が使用する libpq のバージョンを判別するには
  1. Linux ベースのコンピュータの Lambda コンソールで、ローテーション関数に移動し、デプロイバンドルをダウンロードします。zip ファイルを作業ディレクトリに解凍します。

  2. コマンドラインの作業ディレクトリで、以下を実行します。

    readelf -a libpq.so.5 | grep RUNPATH

  3. 文字列 PostgreSQL-9.4.x、または 10 未満のメジャーバージョンが表示されている場合、ローテーション関数は scram-sha-256 をサポートしていません。

    • scram-sha-256 をサポートしていないローテーション関数の出力を次に示します。

      0x000000000000001d (RUNPATH) Library runpath: [/local/p4clients/pkgbuild-a1b2c/workspace/build/PostgreSQL/PostgreSQL-9.4.x_client_only.123456.0/AL2_x86_64/DEV.STD.PTHREAD/build/private/tmp/brazil-path/build.libfarm/lib:/local/p4clients/pkgbuild-a1b2c/workspace/src/PostgreSQL/build/private/install/lib]

    • scram-sha-256 をサポートしているローテーション関数の出力を次に示します。

      0x000000000000001d (RUNPATH) Library runpath: [/local/p4clients/pkgbuild-a1b2c/workspace/build/PostgreSQL/PostgreSQL-10.x_client_only.123456.0/AL2_x86_64/DEV.STD.PTHREAD/build/private/tmp/brazil-path/build.libfarm/lib:/local/p4clients/pkgbuild-a1b2c/workspace/src/PostgreSQL/build/private/install/lib]

    • scram-sha-256 をサポートしているローテーション関数の出力を次に示します。

      0x000000000000001d (RUNPATH) Library runpath: [/local/p4clients/pkgbuild- a1b2c /workspace/build/PostgreSQL/PostgreSQL-14.x_client_only. 123456 .0/AL2_x86_64/DEV.STD.PTHREAD/build/private/tmp/brazil-path/build.libfarm/lib:/local/p4clients/pkgbuild- a1b2c /workspace/src/PostgreSQL/build/private/install/lib]

    • scram-sha-256 をサポートしているローテーション関数の出力を次に示します。

      0x000000000000001d (RUNPATH) Library runpath: [/local/p4clients/pkgbuild- a1b2c/workspace/build/PostgreSQL/PostgreSQL- 14.x_client_only.123456.0/AL2_x86_64/DEV.STD.PTHREAD/build/private/tmp/brazil- path/build.libfarm/lib:/local/p4clients/pkgbuild- a1b2c/workspace/src/PostgreSQL/build/private/install/lib]

注記

2021 年 12 月 30 日より前に自動シークレットローテーションを設定した場合、ローテーション関数には scram-sha-256 をサポートしていない前のバージョンの libpq がバンドルされています。scram-sha-256 をサポートするには、ローテーション関数を再作成する必要があります。

データベースには SSL/TLS アクセスが必要です。

SSL/TLS 接続が必要なデータベースを使用しているが、ローテーション関数が暗号化されていない接続を使用する場合、ローテーション関数はデータベースに接続できません。Amazon RDS (Oracle と Db2 を除く) および Amazon DocumentDB のローテーション関数では、使用可能な場合、データベースへの接続に Secure Sockets Layer (SSL) または Transport Layer Security (TLS) が使用されます。使用できない場合は、暗号化されていない接続が使用されます。

注記

2021 年 12 月 20 日より前に自動シークレットローテーションを設定した場合は、ローテーション関数が SSL/TLS をサポートしていない前のテンプレートに基づいている可能性があります。SSL/TLS を使用する接続をサポートするには、ローテーション関数を再作成する必要があります。

ローテーション関数がいつ作成されたかを特定するには
  1. Secrets Manager コンソール (https://console.aws.amazon.com/secretsmanager/) で、シークレットを開きます。[Rotation configuration] (ローテーション構成) セクションの [Lambda rotation function] (Lambda ローテーション関数) の下に、[Lambda function ARN] (Lambda 関数 ARN) が表示されます (arn:aws:lambda:aws-region:123456789012:function:SecretsManagerMyRotationFunction など)。ARN の末尾から関数名をコピーします (この例では SecretsManagerMyRotationFunction )。

  2. AWS Lambda コンソール (https://console.aws.amazon.com/lambda/) の [Functions] (関数) で、Lambda 関数名を検索ボックスに貼り付けて、[Enter] (入力) を選択してから、Lambda 関数を選択します。

  3. 関数の詳細ページで、[Configuration] (設定) タブの [Tags] (タグ) で、キー aws:cloudformation:stack-name の横にある値をコピーします。

  4. AWS CloudFormation コンソール (https://console.aws.amazon.com/cloudformation) の [Stacks] (スタック) で、キー値を検索ボックスに貼り付けてから、[Enter] (入力) を選択します。

  5. スタックのリストがフィルタリングされ、Lambda ローテーション関数を作成したスタックだけが表示されます。[Created date] (作成日) 列に、スタックが作成された日付が表示されます。これが、Lambda ローテーション関数が作成された日付です。

エラー: 「モジュール 'lambda_function' をインポートできません」

古い (Python 3.7 から新しいバージョンの Python に自動的にアップグレードされた) Lambda 関数を実行している場合に、このエラーが表示されることがあります。このエラーを解決するには、Lambda 関数のバージョンを Python 3.7 に戻してから、既存のローテーション関数を Python 3.7 から 3.9 にアップグレードする を実行します。詳細については、「AWS re:Post」の「Secrets Manager Lambda 関数のローテーションが「pg モジュールが見つかりません」というエラーで失敗したのはなぜですか?」を参照してください。

既存のローテーション関数を Python 3.7 から 3.9 にアップグレードする

2022 年 11 月よりも前に作成された一部のローテーション関数では、Python 3.7 が使用されていました。AWS SDK for Python は、2023 年 12 月に Python 3.7 のサポートを終了しました。詳細については、「AWS SDK およびツールの Python サポートポリシーに関する最新情報」を参照してください。Python 3.9 を使用する新しいローテーション関数に切り替えるには、既存のローテーション関数にランタイムプロパティを追加するか、またはローテーション関数を再作成します。

Python 3.7 を使用する Lambda ローテーション関数を見つけるには
  1. AWS マネジメントコンソール にサインインして AWS Lambda コンソール (https://console.aws.amazon.com/lambda/) を開きます。

  2. [関数] のリストで、SecretsManager をフィルタリングします。

  3. フィルタリングされた関数のリストの [ランタイム] で、Python 3.7 を見つけます。

オプション 1: CloudFormation を使用してローテーション関数を再作成する

Secrets Manager コンソールを使用してローテーションをオンにすると、Secrets Manager は Lambda ローテーション関数などの必要なリソースを作成するために CloudFormation を使用します。コンソールを使用してローテーションをオンにした場合、または CloudFormation スタックを使用してローテーション関数を作成した場合は、同じ CloudFormation スタックを使用して新しい名前でローテーション関数を再作成できます。新しい関数は、より新しいバージョンの Python を使用します。

ローテーション関数を作成した CloudFormation スタックを見つけるには
  • Lambda 関数の詳細ページの [設定] タブで、[タグ] を選択します。aws:cloudformation:stack-id の横にある ARN を表示します。

    次の例に示すように、スタック名は ARN に埋め込まれます。

    • ARN: arn:aws:cloudformation:us-west-2:408736277230:stack/SecretsManagerRDSMySQLRotationSingleUser5c2-SecretRotationScheduleHostedRotationLambda-3CUDHZMDMBO8/79fc9050-2eef-11ed-80f0-021fb13c0537

    • スタック名: SecretsManagerRDSMySQLRotationSingleUser5c2-SecretRotationScheduleHostedRotationLambda

ローテーション関数を再作成するには (CloudFormation)
  1. CloudFormation で、名前でスタックを検索し、[更新] を選択します。

    ルートスタックの更新を推奨するダイアログボックスが表示された場合は、[ルートスタックに移動] を選択し、[更新] を選択します。

  2. [スタックの更新] ページで、[テンプレートの準備] から [Application Composer で編集] を選択し、次に [Application Composer でテンプレートを編集] から [Application Composer で編集] を選択します。

  3. Application Composer で、次の操作を行います。

    1. テンプレートコードの SecretRotationScheduleHostedRotationLambda で、"functionName": "SecretsManagerTestRotationRDS" の値を新しい関数名 (JSON の "functionName": "SecretsManagerTestRotationRDSupdated" など) に置き換えます

    2. [テンプレートの更新] を選択します。

    3. [CloudFormation に進む] ダイアログボックスで、[確認して CloudFormation に進む] を選択します。

  4. CloudFormation スタックワークフローを続行し、[送信] を選択します。

オプション 2: CloudFormation を使用して、既存のローテーション関数のランタイムを更新する

Secrets Manager コンソールを使用してローテーションをオンにすると、Secrets Manager は Lambda ローテーション関数などの必要なリソースを作成するために CloudFormation を使用します。コンソールを使用してローテーションをオンにした場合、または CloudFormation スタックを使用してローテーション関数を作成した場合は、同じ CloudFormation スタックを使用してローテーション関数のランタイムを更新できます。

ローテーション関数を作成した CloudFormation スタックを見つけるには
  • Lambda 関数の詳細ページの [設定] タブで、[タグ] を選択します。aws:cloudformation:stack-id の横にある ARN を表示します。

    次の例に示すように、スタック名は ARN に埋め込まれます。

    • ARN: arn:aws:cloudformation:us-west-2:408736277230:stack/SecretsManagerRDSMySQLRotationSingleUser5c2-SecretRotationScheduleHostedRotationLambda-3CUDHZMDMBO8/79fc9050-2eef-11ed-80f0-021fb13c0537

    • スタック名: SecretsManagerRDSMySQLRotationSingleUser5c2-SecretRotationScheduleHostedRotationLambda

ローテーション関数のランタイムを更新するには (CloudFormation)
  1. CloudFormation で、名前でスタックを検索し、[更新] を選択します。

    ルートスタックの更新を推奨するダイアログボックスが表示された場合は、[ルートスタックに移動] を選択し、[更新] を選択します。

  2. [スタックの更新] ページで、[テンプレートの準備] から [Application Composer で編集] を選択し、次に [Application Composer でテンプレートを編集] から [Application Composer で編集] を選択します。

  3. Application Composer で、次の操作を行います。

    1. テンプレート JSON で、SecretRotationScheduleHostedRotationLambdaPropertiesParameters"runtime": "python3.9" を追加します。

    2. [テンプレートの更新] を選択します。

    3. [CloudFormation に進む] ダイアログボックスで、[確認して CloudFormation に進む] を選択します。

  4. CloudFormation スタックワークフローを続行し、[送信] を選択します。

オプション 3: AWS CDK ユーザー向けに CDK ライブラリをアップグレードする

バージョン v2.94.0 よりも前の AWS CDK を使用してシークレットのローテーションを設定した場合は、v2.94.0 以降にアップグレードすることで Lambda 関数を更新できます。詳細については、「AWS Cloud Development Kit (AWS CDK) v2 デベロッパーガイド」を参照してください。

既存のローテーション関数を Python 3.9 から 3.10 にアップグレードする

Secrets Manager は Lambda ローテーション関数を Python 3.9 から 3.10 に移行しています。Python 3.10 を使用する新しいローテーション関数に切り替えるには、デプロイ方法に基づいてアップグレードパスに従う必要があります。次の手順を使用して、Python バージョンと基盤となる依存関係の両方をアップグレードします。

Python 3.9 を使用する Lambda ローテーション関数を見つけるには
  1. AWS マネジメントコンソール にサインインして AWS Lambda コンソール (https://console.aws.amazon.com/lambda/) を開きます。

  2. [関数] のリストで、SecretsManager をフィルタリングします。

  3. フィルタリングされた関数のリストの [ランタイム] で、Python 3.9 を見つけます。

デプロイ方法によるパスの更新

このリストで識別される Lambda ローテーション関数は、Secrets Manager コンソール、AWS Serverless Application Repository アプリケーション、または CloudFormation 変換を使用してデプロイできます。これらのデプロイ戦略ごとに個別の更新パスがあります。

関数のデプロイ方法に応じて、次のいずれかの手順を使用して Lambda ローテーション関数を更新します。

AWS Secrets Manager console-deployed functions

既存の Lambda 関数の依存関係を手動で更新することはできないため、新しい Lambda 関数は AWS Secrets Manager コンソールを介してデプロイする必要があります。

AWS Secrets Manager コンソールにデプロイされた関数をアップグレードするには、次の手順に従います。

  1. Secrets Manager のコンソール (https://console.aws.amazon.com/secretsmanager/) を開きます。

  2. AWS Secrets Manager で、[シークレット] を選択します。更新する Lambda 関数を使用するシークレットを選択します。

  3. [ローテーション] タブに移動し、[ローテーション設定の更新] オプションを選択します。

  4. [ローテーション関数][新しい関数を作成する] を選択し、Lambda ローテーション関数の名前を入力します。

    1. (オプション) 更新が完了したら、更新された Lambda 関数をテストして、正常に動作することを確認できます。[ローテーション] タブで、[シークレットの即時ローテーション] を選択して、即時ローテーションを開始します。

    2. (オプション) 関数ログと、実行時に Amazon CloudWatch で使用される Python バージョンを表示できます。詳細については、「AWS Lambda 開発者ガイド」の「Lambda 関数の CloudWatch Logs を表示する」を参照してください。

  5. 新しいローテーション関数を設定したら、古いローテーション関数を削除できます。

AWS Serverless Application Repository deployments

次の手順では、AWS Serverless Application Repository デプロイをアップグレードする方法について説明します。AWS Serverless Application Repository を介してデプロイされた Lambda 関数には、関数が属する Lambda アプリケーションへのリンクを含む、This function belongs to an application. Click here to manage it. が表示されているバナーがあります。

重要

AWS Serverless Application Repository の可用性は、AWS リージョン によって異なります。

AWS Serverless Application Repository にデプロイされた関数を更新するには、次の手順に従います。

  1. AWS Lambda コンソールの https://console.aws.amazon.com/lambda/ を開いてください。

  2. 更新する必要がある Lambda 関数の [設定] タブに移動します。

    1. デプロイされた AWS Serverless Application Repository アプリケーションを更新するときは、関数に関する次の情報が必要になります。この情報は、Lambda コンソールで確認できます。

      • Lambda アプリケーションの名前

        • Lambda アプリケーション名は、バナーのリンクを使用して確認できます。たとえば、バナーには次の serverlessrepo-SecretsManagerRedshiftRotationSingleUser が表示されます。この例では、名前は SecretsManagerRedshiftRotationSingleUser です。

      • Lambda ローテーション関数名

      • Secrets Manager エンドポイント

        • エンドポイントは、SECRETS_MANAGER_ENDPOINT 変数に割り当てられた [設定][環境変数] タブにあります。

  3. Python をアップグレードするには、サーバーレスアプリケーションのセマンティックバージョンを更新する必要があります。「AWS Serverless Application Repository デベロッパーガイド」の「アプリケーションの更新」を参照してください。

Custom Lambda rotation functions

カスタム Lambda ローテーション関数を作成した場合は、これらの関数の各パッケージの依存関係とランタイムをアップグレードする必要があります。詳細については、「Lambda 関数ランタイムを最新バージョンにアップグレードする」を参照してください。

AWS::SecretsManager-2024-09-16 transform macro

Lambda 関数がこの変換を通じてデプロイされている場合、既存のテンプレートを使用してスタックを更新すると、更新された Lambda ランタイムを使用できます。

既存のテンプレートを使用して CloudFormation スタックを更新するには、次の手順に従います。

  1. https://console.aws.amazon.com/cloudformation で CloudFormation コンソール を開きます。

  2. [スタック] ページで、更新する実行中のスタックを選択します。

  3. スタックの詳細ペインで、[更新] を選択します。

  4. [テンプレートの更新方法を選択する] で、[直接更新] を選択します。

  5. [テンプレートの指定] ページで、[既存のテンプレートを使用する] を選択します。

  6. 他のすべてのオプションをデフォルト値のままにして、[スタックの更新] を選択します。

スタックの更新で問題が発生した場合は、「CloudFormation ユーザーガイド」の「スタックが失敗する原因を判断する」を参照してください。

AWS::SecretsManager-2020-07-23 transform macro

AWS::SecretsManager-2020-07-23 を使用している場合は、新しい変換バージョンに移行することをお勧めします。詳細については、AWS セキュリティブログの「AWS Secrets Manager 変換の拡張バージョンの導入: AWS::SecretsManager-2024-09-16」を参照してください。AWS::SecretsManager-2020-07-23 を引き続き使用する場合、ランタイムバージョンと Lambda 関数コードアーティファクトの間に不一致エラーが発生する可能性があります。詳細については、「CloudFormation テンプレートリファレンス」の「AWS「::SecretsManager::RotationSchedule HostedRotationLambda」を参照してください。

スタックの更新で問題が発生した場合は、「CloudFormation ユーザーガイド」の「スタックが失敗する原因を判断する」を参照してください。

Python アップグレードの検証

Python のアップグレードを確認するには、Lambda コンソール (https://console.aws.amazon.com/lambda/) を開き、[関数] ページにアクセスします。更新した関数を選択します。[コードソース] セクションで、ディレクトリに含まれているファイルを確認し、Python .so ファイルがバージョン 3.10 であることを確認します。

AWS Lambda シークレットのローテーションが PutSecretValue で失敗した

Secrets Manager で引き受けたロールまたはクロスアカウントローテーションを使用していて、CloudTrail で次のメッセージを含む RotationFailed イベントが見つかった場合: 「Pending secret version VERSION_ID for Secret SECRET_ARN was not created by Lambda LAMBDA_ARN.」。AWSPENDING ステージングラベルを削除してローテーションを再起動し、RotationToken パラメータを使用するように Lambda 関数を更新する必要があります。

Lambda ローテーション関数を更新して RotationToken を含める

  1. Lambda 関数コードをダウンロードする

    • Lambda のコンソールを開く

    • ナビゲーションペインで、[関数] を選択する

    • 関数名の Lambda シークレットローテーション関数を選択する

    • ダウンロードでは、関数コード .zipAWS SAM ファイル両方のいずれかを選択します。

    • [OK] を選択して、ローカルマシンに関数を保存します。

  2. Lambda_handler を編集する

    クロスアカウントローテーションの create_secret ステップに rotation_token パラメータを含めます:

    def lambda_handler(event, context): """Secrets Manager Rotation Template This is a template for creating an AWS Secrets Manager rotation lambda Args: event (dict): Lambda dictionary of event parameters. These keys must include the following: - SecretId: The secret ARN or identifier - ClientRequestToken: The ClientRequestToken of the secret version - Step: The rotation step (one of createSecret, setSecret, testSecret, or finishSecret) - RotationToken: the rotation token to put as parameter for PutSecretValue call context (LambdaContext): The Lambda runtime information Raises: ResourceNotFoundException: If the secret with the specified arn and stage does not exist ValueError: If the secret is not properly configured for rotation KeyError: If the event parameters do not contain the expected keys """ arn = event['SecretId'] token = event['ClientRequestToken'] step = event['Step'] # Add the rotation token rotation_token = event['RotationToken'] # Setup the client service_client = boto3.client('secretsmanager', endpoint_url=os.environ['SECRETS_MANAGER_ENDPOINT']) # Make sure the version is staged correctly metadata = service_client.describe_secret(SecretId=arn) if not metadata['RotationEnabled']: logger.error("Secret %s is not enabled for rotation" % arn) raise ValueError("Secret %s is not enabled for rotation" % arn) versions = metadata['VersionIdsToStages'] if token not in versions: logger.error("Secret version %s has no stage for rotation of secret %s." % (token, arn)) raise ValueError("Secret version %s has no stage for rotation of secret %s." % (token, arn)) if "AWSCURRENT" in versions[token]: logger.info("Secret version %s already set as AWSCURRENT for secret %s." % (token, arn)) return elif "AWSPENDING" not in versions[token]: logger.error("Secret version %s not set as AWSPENDING for rotation of secret %s." % (token, arn)) raise ValueError("Secret version %s not set as AWSPENDING for rotation of secret %s." % (token, arn)) # Use rotation_token if step == "createSecret": create_secret(service_client, arn, token, rotation_token) elif step == "setSecret": set_secret(service_client, arn, token) elif step == "testSecret": test_secret(service_client, arn, token) elif step == "finishSecret": finish_secret(service_client, arn, token) else: raise ValueError("Invalid step parameter")
  3. create_secret コードの編集

    rotation_token パラメータを受け入れて使用するように create_secret 関数を改訂します:

    # Add rotation_token to the function def create_secret(service_client, arn, token, rotation_token): """Create the secret This method first checks for the existence of a secret for the passed in token. If one does not exist, it will generate a new secret and put it with the passed in token. Args: service_client (client): The secrets manager service client arn (string): The secret ARN or other identifier token (string): The ClientRequestToken associated with the secret version rotation_token (string): the rotation token to put as parameter for PutSecretValue call Raises: ResourceNotFoundException: If the secret with the specified arn and stage does not exist """ # Make sure the current secret exists service_client.get_secret_value(SecretId=arn, VersionStage="AWSCURRENT") # Now try to get the secret version, if that fails, put a new secret try: service_client.get_secret_value(SecretId=arn, VersionId=token, VersionStage="AWSPENDING") logger.info("createSecret: Successfully retrieved secret for %s." % arn) except service_client.exceptions.ResourceNotFoundException: # Get exclude characters from environment variable exclude_characters = os.environ['EXCLUDE_CHARACTERS'] if 'EXCLUDE_CHARACTERS' in os.environ else '/@"\'\\' # Generate a random password passwd = service_client.get_random_password(ExcludeCharacters=exclude_characters) # Put the secret, using rotation_token service_client.put_secret_value(SecretId=arn, ClientRequestToken=token, SecretString=passwd['RandomPassword'], VersionStages=['AWSPENDING'], RotationToken=rotation_token) logger.info("createSecret: Successfully put secret for ARN %s and version %s." % (arn, token))
  4. 更新された Lambda 関数コードをアップロードする

    Lambda 関数コードを更新したら、アップロードしてシークレットをローテーションします。

CreateSecretSetSecret の間など、Lambda 関数がセットのループで停止して、シークレットローテーションが断続的に失敗する場合、問題は同時実行設定に関連している可能性があります。

同時実行のトラブルシューティング手順

警告

プロビジョニングされた同時実行パラメータを 10 未満の値に設定すると、Lambda 関数の実行スレッドが不十分であるためにスロットリングが発生する可能性があります。詳細については、「AWS Lambda AWS Lambda デベロッパーガイド」の「予約済み同時実行数とプロビジョニングされた同時実行数について」を参照してください。

  1. Lambda の同時実行設定を確認して調整します:

    • reserved_concurrent_executions の値がが低すぎないことを確認する (例: 1)

    • 予約された同時実行を使用する場合は、少なくとも 10 に設定する

    • 柔軟性を高めるために、予約されていない同時実行の使用を検討する

  2. プロビジョニングされた同時実行の場合:

    • プロビジョニングされた同時実行パラメータを明示的に設定しないでください (Terraform など)。

    • 設定する必要がある場合は、10 以上の値を使用します。

    • 選択した値がユースケースで機能することを徹底的にテストします。

  3. 同時実行をモニタリングして調整します:

    • 次の式を使用して同時実行数を計算します。同時実行数 = (1 秒あたりの平均リクエスト数) * (秒単位の平均リクエスト時間)。詳細については、「予約済み同時実行数の見積もり」 (Estimating reserved concurrency) を参照してください。

    • ローテーション中に値を観察して記録し、適切な同時実行設定を決定します。

    • 低い同時実行値を設定するときは注意してください。使用可能な実行スレッドが足りない場合、スロットリングが発生する可能性があります。

Lambda 同時実行の設定の詳細については、「AWS Lambda デベロッパーガイド」の「予約された同時実行数の設定」および「プロビジョニングされた同時実行数の設定」を参照してください。