AWS Step Functions のワークフロー設計

AWS Step Functions のステートマシン、Amazon States Language、分岐・並列処理・エラー制御、Standard と Express の違い、SNS・SQS との使い分けを学びます。

学習順Step 203 / 203サービス連携試験ドメイン弾力性

AWS Step Functions によるワークフローオーケストレーション

AWS Step Functions は、アプリケーションの処理をステートマシンとして定義し、複数のタスクや AWS サービスを連携させるワークフローサービスです。実行中の状態、次に進む条件、エラー時の動作をワークフローに記述できます。Lambda 関数の呼び出しだけでなく、対応する AWS サービスの API を直接呼び出すサービス統合も利用できます。

処理の順序をアプリケーションコードの中に埋め込む代わりに、フローを可視化して制御をサービス側に任せられます。各処理を独立して変更・拡張しやすくなり、失敗した段階の追跡や再試行もワークフロー単位で管理できます。Workflow Studio で視覚的に作成する方法と、定義をコードとして管理する方法のどちらも選べます。

ステートマシンと状態

ステートマシンは、**状態(state)**と状態間の遷移からなる処理の設計図です。実行時には、入力を受け取って開始状態から処理を進め、状態ごとにタスクを実行したり、条件に基づいて遷移先を選んだりします。完了状態に到達するか、失敗状態になると実行が終わります。

条件分岐と並列処理を含むStep Functionsのステートマシン

この例では、まず入力を検査します。条件を満たさなければ失敗として終了し、問題がなければ互いに依存しない更新と通知を並列に実行します。並列ブランチの完了後に待機し、最後にワークフローを完了します。どの状態で何を行い、どこへ進むのかが定義に表れるため、処理の流れと障害時の経路を確認しやすくなります。

主な状態タイプ

Step Functions のステートマシンは、状態タイプを組み合わせて処理を表現します。試験では、状態名と用途の対応に加えて、似た並列処理の使い分けが問われます。

状態タイプ 役割 使いどころ
Task Lambda 関数、AWS サービス API、Activity などの実処理を呼び出す データの変換、通知の送信、データベース更新など
Choice 入力値などの条件を評価し、遷移先を選ぶ 承認状態による分岐、処理対象による経路の切り替え
Wait 指定秒数または指定時刻まで実行を一時停止する 受付後の猶予時間、処理間隔の調整、予定時刻までの保留
Parallel 複数のブランチを同時に実行し、すべてのブランチが完了してから次へ進む 同じ入力を使う独立した複数処理
Map 配列の各要素に対して同じ処理を繰り返し、要素単位の実行を並列化する レコードの集合やファイル内の項目を個別に処理
Pass 実処理を呼び出さずに入力をそのまま渡す、または定数を追加する 入力の整形、状態遷移の確認、簡単なデータ受け渡し
Succeed 成功としてステートマシンを終了する 明示的な正常終了地点
Fail エラー名や原因を示して失敗として終了する 回復できない入力や処理を検出した地点

Parallel と Map の違いは、何を並行化するかです。Parallel は「検索用の更新」と「通知」のように、あらかじめ定義した異なる処理ブランチを同時に実行します。Map は配列の要素ごとに同じ処理一式を適用します。Map では同時実行数を制御でき、大きなデータセットには Distributed Map を使える場合もあります。後続の状態へ進む前に、Map の項目処理は完了します。

Wait は実行を止めるために Lambda を待機させ続ける手段ではありません。相対秒数またはタイムスタンプを使い、ワークフローの状態として待ち時間を表します。期限を過ぎたら通知する、一定時間後に再確認するなど、処理時刻の制御に使えます。

Activity は状態タイプの名称ではなく、外部ワーカーが処理を受け持つタスクの仕組みです。ステートマシンの Task 状態が Activity ARN を参照し、ワーカー側は Step Functions からタスクを取得して実行します。完了時に成功または失敗を返すため、Lambda などのサービス統合とは異なり、ワーカーの実装・稼働管理が必要です。長時間の外部処理や、AWS サービス統合に直接対応しない処理で選択肢になります。

Amazon States Language(ASL)で定義する

**Amazon States Language(ASL)**は、ステートマシンを定義する JSON ベースの言語です。各状態の名前とタイプ、実行するリソース、入力・出力の受け渡し、次の遷移先、終了条件などを記述します。JSONPath または JSONata のクエリ言語を用いたデータ処理にも対応しています。

次の例は、Lambda を呼び出す Task 状態の構造を示しています。関数名は環境に応じて置き換えます。

{
  "PrepareManifest": {
    "Type": "Task",
    "Resource": "arn:aws:states:::lambda:invoke",
    "Parameters": {
      "FunctionName": "arn:aws:lambda:us-east-1:123456789012:function:prepare-manifest",
      "Payload.$": "$"
    },
    "ResultPath": "$.manifest",
    "Retry": [
      {
        "ErrorEquals": ["Lambda.ServiceException", "Lambda.TooManyRequestsException"],
        "IntervalSeconds": 2,
        "MaxAttempts": 3,
        "BackoffRate": 2
      }
    ],
    "Catch": [
      {
        "ErrorEquals": ["States.ALL"],
        "ResultPath": "$.error",
        "Next": "RecordFailure"
      }
    ],
    "Next": "ContinueWorkflow"
  }
}

Parameters で呼び出し先に渡す値を組み立て、ResultPath でタスクの結果を実行データのどこに格納するかを指定しています。Retry は対象のエラーを再試行し、Catch は再試行後も失敗した場合などに別の状態へ進ませます。Next は次の状態を指定し、終端状態では End: true などで終了を示します。ステートマシン全体では開始状態を StartAt に指定します。

JSONPath を使う定義では、InputPath、Parameters、ResultSelector、ResultPath、OutputPath などを使って状態間のデータを絞り込み、整形します。これらの設定がない場合も各状態は入力を受け取り、Task やブランチの実行結果を次の状態へ引き渡します。入力が増え続けないように必要な項目だけを渡し、ステートマシンの履歴やサービス統合のペイロード制限を考慮してください。

再試行とエラー処理

分散システムでは、一時的なスロットリングやネットワーク障害など、再試行で回復できるエラーが起こり得ます。Step Functions では Task などの状態に Retry と Catch を定義し、回復可能な失敗と、別経路へ移すべき失敗を分けられます。

  • Retry:指定したエラーに対して、待ち時間・試行回数・間隔の増加率を設定して再実行する。
  • Catch:再試行上限に達した失敗を受け取り、補償処理、失敗記録、担当者への通知など別の状態へ遷移させる。
  • Fail:処理を継続できない場合に、エラー名や原因を付けて実行を失敗で終了する。

再試行は成功するまで何度でも行う機能ではありません。MaxAttempts などの上限と、重複実行されても問題が起きないかを確認します。外部システムへの書き込みや決済などで再試行が同じ副作用を繰り返すと問題になる場合は、冪等性キーや重複検出を設計します。Standard の「Exactly-once」も、明示した Retry の反復や下流サービスの配信・処理保証まで一括して一度にするものではありません。

ワークフローの起動方法

ステートマシンは、Step Functions の StartExecution API / SDK / CLI から開始できます。また、他サービスのイベントや API リクエストを起点にする構成もあります。

  • EventBridge:ルールに一致した AWS サービスイベントなどからステートマシンを起動する。たとえば、オブジェクト登録イベントを契機に後続処理を始める。以前の CloudWatch Events は EventBridge に統合された名称である。
  • API Gateway:API メソッドから Step Functions の実行開始 API を呼び出し、クライアント要求に応じて処理を開始する。API Gateway と同期 Express 実行を統合する構成では、実行結果を API 応答に含められる。
  • サービス統合:ステートマシンの Task 状態から、他の AWS サービスの API を直接呼び出す。別の Lambda を挟まずにサービス間の処理をつなげられる場合がある。

EventBridge はイベントを条件に合わせて配送する役割、Step Functions は起動後の処理順序と状態遷移を管理する役割です。両者は競合サービスではなく、EventBridge を起動元、Step Functions をワークフローの実行役として組み合わせられます。

Standard と Express の選択

ステートマシンの作成時に Standard または Express を選択します。ワークフロータイプは作成後に変更できないため、最大実行時間、実行頻度、処理の再実行可能性、監査要件、サービス統合パターンをあわせて判断します。

比較項目 Standard Express
主な用途 長時間実行、耐久性・監査性が重要な業務ワークフロー 短時間で高頻度に実行するイベント処理
最大実行時間 最大1年 最大5分
実行回数に関する意味 通常は Exactly-once。定義した Retry による再実行は別途起こる 非同期実行は At-least-once。同じ入力が複数回処理されても安全な設計が必要
同期実行 非対応 同期 Express は At-most-once の実行モデルで結果を同期的に返せる
履歴 Step Functions API から実行履歴を確認できる CloudWatch Logs へ履歴を出力する。ログレベル等の設定と CloudWatch Logs の料金を考慮
サービス統合パターン Request Response、対応するサービスで Run a Job(.sync)や Wait for Callback(.waitForTaskToken)も利用可能 Request Response を利用。Standard が持つ .sync と Callback の統合パターンには対応しない
料金の基準 状態遷移数 実行回数、実行時間、使用メモリ

Standard は、1時間を超える処理、承認待ち、処理履歴の確認、長いジョブの完了待ちなどに向いています。Express は、最大5分以内に完了する高頻度の処理や API バックエンドなどに向きます。Express は非同期と同期で実行の保証が異なります。非同期は At-least-once なので重複実行に耐えるようにし、同期実行は At-most-once の意味を理解したうえで選択してください。

どちらを選んでも、サービス統合とクォータには個別の条件があります。特定のサービス呼び出しが .sync や Callback を必要とするなら、その統合パターンをサポートする Standard が必要です。短時間かどうかだけでなく、処理保証と連携方法も選択条件です。

Step Functions、SNS、SQS の使い分け

3サービスはいずれもサーバーレスアーキテクチャで使われますが、解決する課題が異なります。

サービス 中心となる役割 得意な処理
Step Functions 状態と処理手順のオーケストレーション 複数段階の処理、条件分岐、並列ブランチ、実行待ち、再試行、失敗後の補償
Amazon SNS Pub/Sub によるイベントのファンアウト 1つのイベントを複数の購読先へ配信する通知
Amazon SQS キューによる非同期タスクのバッファリング 処理要求を蓄積し、コンシューマーが自分の処理速度で受け取るワークキュー

SNS で購読者に直接通知する構成は、イベントに応じて簡単な独立処理を呼び出す場合に使えます。処理側の都合で受け取りを遅らせたり、滞留分をキューに保持したりしたい場合は SQS を使います。SNS から複数の SQS キューへ配信すれば、複数の処理系を互いに独立したペースで動かすファンアウトもできます。

Step Functions は SNS のような Pub/Sub 配信サービスではありません。イベントの送信先を増やすだけなら SNS、処理要求をためてワーカー数を調整するなら SQS、順序・分岐・待機・回復処理を含む一連の処理を管理するなら Step Functions を検討します。これらは一緒に使うこともできます。たとえば EventBridge で実行を開始し、Step Functions が条件分岐を行い、各 Task から SQS や Lambda を呼び出せます。

独立した大量タスクにはキューとワーカーを検討する

たとえば、在庫カタログの更新要求を商品ごとに独立して処理するサービスで、更新対象が増え、すべての取り込みが完了するまで長い時間がかかるとします。各商品に必要な処理が単一の Lambda 実行で完結し、項目同士に順序や状態の依存がないなら、受付側が要求を SQS に送信し、Lambda の SQS イベントソースマッピングでメッセージをバッチ取得して処理する構成が候補になります。

SQSで処理要求を蓄積し、Lambdaワーカーがバッチで独立タスクを処理する構成

キューが一時的な要求の増加を吸収し、Lambda はバッチサイズや同時実行数の設定に応じて処理を並列化できます。ワーカーが処理できる速度よりも要求の到着が速ければキューに滞留するため、キュー長、メッセージ滞留時間、Lambda の同時実行数を監視し、必要に応じてバッチサイズやスケーリングを調整します。SQS を使っても Lambda の処理能力が無制限に上がるわけではなく、下流データベースなどの容量も考慮が必要です。

ここで Step Functions を選ぶかどうかは、「複数の入力があるか」「並列実行したいか」だけでは決まりません。Step Functions の Map は配列の項目を並列に処理できますが、各項目で状態を追跡する、複数段階を順序立てる、再試行や失敗経路を実行単位で管理するなど、オーケストレーションが必要な場合に有効です。単一の独立処理を大量に流すだけなら、ワークフローの状態管理が要件に対して過剰にならないか、SQS と Lambda の構成と料金・運用負荷を比較します。

タスクの前後に条件分岐や補償処理がなく、各メッセージを同じ Lambda で処理できるなら、Step Functions を経由させる必要はありません。SQS と Lambda のイベントソースマッピングには失敗メッセージを再試行する仕組みがあり、処理に繰り返し失敗するメッセージはデッドレターキューへ移す構成も取れます。ワークフローとして各段階の状態や回復経路を管理する必要が生じた時点で、Step Functions を追加するか検討します。

SNS も単独でキューの代用にはなりません。購読先に通知をファンアウトする必要があれば SNS を使い、各処理先の独立したバッファリングや再試行が必要なら SNS と SQS を組み合わせます。「SNS は常に Step Functions より安い」といった一般則ではなく、配信先の数、メッセージ量、バッファリング、処理状態の追跡要件、下流サービスの費用を含めて比較してください。

料金を比較する

Standard は、ステートマシンの実行中に発生した状態遷移数に応じて課金されます。ワークフロー内の処理が進むほど遷移数が増え、Retry で状態が再実行された場合も追加の遷移として数えられます。AWS Step Functions の料金ページには月間4,000回分の無料状態遷移枠が記載されていますが、無料枠や料金条件は変更される可能性があるため、利用時点の公式料金ページで確認してください。

Express は状態遷移数ではなく、実行回数、実行時間、使用メモリをもとに料金が決まります。CloudWatch Logs へ実行履歴を送る場合は、そのログ取り込み・保管料金も加わります。実行が短時間でもデータ処理量やログ量によって費用が変わるため、想定件数と処理時間で見積もります。

大量の単純なイベントをすべて Step Functions の実行にすると、Standard では実行件数と各実行の遷移数が費用に影響します。一方、Express がいつでも最安になるわけでもありません。実行パターンに応じた料金モデルを選び、Step Functions、SQS、SNS、Lambda それぞれのリクエスト・処理・ログの費用を合わせて確認します。

試験での選択ポイント

  • 複数段階の処理、条件分岐、失敗時の再試行や補償処理が必要なら Step Functions を考える。
  • 複数の独立したブランチを同時に実行するなら Parallel、配列項目ごとに同じ処理を実行するなら Map を考える。
  • 大量の独立タスクを一時的に蓄積し、処理側をバッチ化・スケールするなら SQS と Lambda のイベントソースマッピングを検討する。
  • 1件のイベントを複数の受信者に同時配信するなら SNS を検討する。受信者ごとにバッファリングするなら SNS と SQS を組み合わせる。
  • 長時間・監査可能な実行には Standard、5分以内の高頻度実行には Express を候補とし、実行の重複可能性、同期実行、.sync / Callback の要否を確認する。
  • 料金は、Standard の状態遷移数、Express の実行回数・時間・メモリ、SQS/SNS のリクエスト数、Lambda の実行時間など、構成する各サービスの課金単位を比較する。

公式ドキュメント

重要ポイント

  • ▸Step Functions は複数サービスや処理を状態機械として組み合わせ、順序・条件分岐・並列実行・エラー処理を管理するオーケストレーションサービス
  • ▸ASL はステートマシンの JSON ベースの定義言語。Task、Choice、Wait、Parallel、Map、Retry、Catch などで処理と制御を表す
  • ▸Standard は長時間・監査向けで最大1年、状態遷移数で課金。Express は最大5分の高頻度処理向けで、実行回数・実行時間・メモリ使用量で課金
  • ▸独立した大量タスクをバッファリングしてワーカー処理するなら SQS、複数の購読先へイベントを配るなら SNS、複数段階の状態を管理するなら Step Functions
  • ▸各タスクの順番や依存関係、再試行、補償・失敗処理が必要かを見極め、単純なイベント配信にオーケストレーションを追加しない

このトピックの学習を完了しますか?

完了状態はいつでも切り替えられます