web-dev-qa-db-ja.com

並列Lambda関数を呼び出すAWS Step Functionでログを無効にする(またはリダイレクトする)方法

並列実行ブランチでAWSステップ関数を実行しています。

各ブランチは個別に成功しますが、全体的な機能は次のエラーで失敗します。

States.DataLimitExceeded-状態/タスクがサービスの最大文字数を超えるサイズの結果を返しました。

次に、AWSからこの問題を説明し、回避策を提案する記事を見つけました。

https://docs.aws.Amazon.com/step-functions/latest/dg/connect-lambda.html

その記事は言う:

Lambda呼び出しAPIは、デフォルトで応答にログを含めます。ワークフローで複数のLambdaを呼び出すと、States.DataLimitExceededエラーが発生する可能性があります。これを回避するには、Lambda関数を呼び出すときにパラメーターとして「LogType」=「None」を含めます。

私の質問は、どこに正確に置くのですか?ステートマシン定義のさまざまな場所に配置しようとしましたが、次のエラーが発生します。

フィールド「LogType」はステップ関数ではサポートされていません

そのエラーはサポート記事に反しているようですので、おそらく私はそれを間違っています!

アドバイスをいただければ幸いです。

乾杯

UPDATE 1:明確にするために、これは26の並列分岐を持つ並列関数です。以下の例のように、各ブランチには小さな出力があります。このデータの最大の項目はLogResultです。これは(base64でデコードされた場合)課金情報のみです。この情報に26を掛けるとエラーが発生したと思うので、このLogResultをオフにしたいだけです!!!

{
  "ExecutedVersion": "$LATEST",
  "LogResult": "U1RBUlQgUmVxdWVzdElkOiBlODJjZTRkOS0zMjk2LTRlNDctYjcyZC1iYmEwMzI1YmM3MGUgVmVyc2lvbjogJExBVEVTVApFTkQgUmVxdWVzdElkOiBlODJjZTRkOS0zMjk2LTRlNDctYjcyZC1iYmEwMzI1YmM3MGUKUkVQT1JUIFJlcXVlc3RJZDogZTgyY2U0ZDktMzI5Ni00ZTQ3LWI3MmQtYmJhMDMyNWJjNzBlCUR1cmF0aW9uOiA3NzI5Ljc2IG1zCUJpbGxlZCBEdXJhdGlvbjogNzgwMCBtcwlNZW1vcnkgU2l6ZTogMTAyNCBNQglNYXggTWVtb3J5IFVzZWQ6IDEwNCBNQglJbml0IER1cmF0aW9uOiAxMTY0Ljc3IG1zCQo=",
  "Payload": {
    "statusCode": 200,
    "body": {
      "signs": 63,
      "nil": ""
    }
  },
  "SdkHttpMetadata": {
    "HttpHeaders": {
      "Connection": "keep-alive",
      "Content-Length": "53",
      "Content-Type": "application/json",
      "Date": "Thu, 21 Nov 2019 04:00:42 GMT",
      "X-Amz-Executed-Version": "$LATEST",
      "X-Amz-Log-Result": "U1RBUlQgUmVxdWVzdElkOiBlODJjZTRkOS0zMjk2LTRlNDctYjcyZC1iYmEwMzI1YmM3MGUgVmVyc2lvbjogJExBVEVTVApFTkQgUmVxdWVzdElkOiBlODJjZTRkOS0zMjk2LTRlNDctYjcyZC1iYmEwMzI1YmM3MGUKUkVQT1JUIFJlcXVlc3RJZDogZTgyY2U0ZDktMzI5Ni00ZTQ3LWI3MmQtYmJhMDMyNWJjNzBlCUR1cmF0aW9uOiA3NzI5Ljc2IG1zCUJpbGxlZCBEdXJhdGlvbjogNzgwMCBtcwlNZW1vcnkgU2l6ZTogMTAyNCBNQglNYXggTWVtb3J5IFVzZWQ6IDEwNCBNQglJbml0IER1cmF0aW9uOiAxMTY0Ljc3IG1zCQo=",
      "x-amzn-Remapped-Content-Length": "0",
      "x-amzn-RequestId": "e82ce4d9-3296-4e47-b72d-bba0325bc70e",
      "X-Amzn-Trace-Id": "root=1-5dd60be1-47c4669ce54d5208b92b52a4;sampled=0"
    },
    "HttpStatusCode": 200
  },
  "SdkResponseMetadata": {
    "RequestId": "e82ce4d9-3296-4e47-b72d-bba0325bc70e"
  },
  "StatusCode": 200
}
7
Timbo

同じ問題で行き詰まりました。ステップ関数は、2つの状態間で受け渡しできるデータに32,768文字の制限を課します。

https://docs.aws.Amazon.com/step-functions/latest/dg/limits.html

多分あなたは問題を考えて別の方法で分解する必要がありますか?それが私がしたことです。ログ応答を削除するとある程度の弾力性が得られますが、ソリューションは特定の制限後に拡張されません。

0
Anss

結果をS3バケットに格納し、ステートマシンにパスを結果ファイルへのパス(およびデータの簡単な要約またはPASS/FAILなどのステータス)を返すようにして、Step Functionsで大きなデータを処理します。

DBを使用したほうが快適であれば、同じことを行うこともできます。

この方法では、結果の現在の形式を変更する必要はありません。大量のデータの代わりに参照を渡すだけで、必要な限り保持されます。

Lambdasの先頭は次のようになり、入力がファイルからのものかプレーンデータからのものかがわかります。

    bucket_name = util.env('BUCKET_NAME')
    if 'result_path' in input_data.keys():
        # Results are in a file that is referenced.
        try: 
            result_path = input_data['result_path']
            result_data = util.get_file_content(result_path, bucket_name)
        except Exception as e:
            report.append(f'Failed to parse JSON from {result_path}: {e}')
    else:
        # Results are just raw data, not a reference.
        result_data = input_data

次に、Lambdaの最後に結果をアップロードし、そのファイルへの道順を返します。

    import boto3
    def upload_results_to_s3(bucket_name, filename, result_data_to_upload):
    try:
        s3 = boto3.resource('s3')
        results_prefix = 'Path/In/S3/'
        results_suffix = '_Results.json'

        result_file_path = '' + results_prefix + filename + results_suffix

        s3.Object(bucket_name, result_file_path).put(
            Body=(bytes(json.dumps(result_data_to_upload, indent=2).encode('UTF-8')))
        )

        return result_file_path



    result_path = upload_results_to_s3(bucket_name, filename, result_data_to_upload)

    result_obj = {
        "result_path": result_path,
        "bucket_name": bucket_name
    }
    return result_obj

次に、ファイルから入力を取得するために、次のLambdaには最初のコードスニペットが含まれます。

ステップ関数ノードは次のようになり、結果はpython上記のコードではresult_objになります。

    "YOUR STATE": 
    { 
        "Comment": "Call Lambda that puts results in file", 
        "Type": "Task", 
        "Resource": "arn:aws:lambda:YOUR LAMBDA ARN", 
        "InputPath": "$.next_function_input", 
        "ResultPath": "$.next_function_input", 
        "Next": "YOUR-NEXT-STATE" 
    }
0
Branson Smith

一週間前に問題がありました。私が解決した方法は以下のようなものです:

結果のどの部分を次のステップに送信するかを定義できます。

そのためにはあなたが使用する必要があります

"出力パス": "$ .part2"、

あなたのjson入力には

"part1":{"portion1":{"procedure": "Delete_X"
}、 "portion2":{"手順": "Load_X"}}、

"part2":{"portion1":{"procedure": "Delete_Y"
}、 "portion2":{"手順": "Load_Y"}}

Part1が処理されたら、part1が出力とそれに関連するresultpathで送信されないようにします。次のステップに必要なパート2だけが次のステップに送られます。これで: "OutputPath": "$ .part2"、

それが役立つかどうか教えてください

0
zip

あなたができることは、あなたのjsonに "emptyOutputPath": ""を追加することです、

"emptyOutputPath": "",

"part1": { "portion1": { "procedure": "Delete_X"
}, "portion2":{ "procedure": "Load_X" } },

"part2": { "portion1": { "procedure": "Delete_Y"
}, "portion2":{ "procedure": "Load_Y" } }

これにより、空の "OutputPath": "$。emptyOutputPath"を実行でき、ResultPathがクリアされます。

それが役に立てば幸い

0
zip

この問題をフォローアップしてループを閉じます。

基本的には、代わりにAQSメッセージキューを使用する代わりに、並列ラムダの使用をあきらめました

0
Timbo