StepFunctions ステートマシン同期実行の挙動

# はじめに
StepFunctionsを用いた開発を行う中で、ステートマシンの同期実行の挙動で気になった点があったので、検証してみた。今回はその検証結果をまとめる。

# ステートマシンの同期実行方法

以下のように呼び出したいステートマシンを `startExecution.sync:2` で呼び出し、`Parameter` の `input` に `"AWS_STEP_FUNCTIONS_STARTED_BY_EXECUTION_ID.$": "$$.Execution.Id"` を入れることで、簡単にステートマシンを同期実行することができる。

```

{
  "Comment": "A description of my state machine",
  "StartAt": "test1",
  "States": {
    "test1": {
      "Type": "Task",
      "Resource": "arn:aws:states:::states:startExecution.sync:2",
      "Parameters": {
        "StateMachineArn": "arn:aws:states:{Region}:{AccountID}:stateMachine:{StateMachineName}",
        "Input": {
          "AWS_STEP_FUNCTIONS_STARTED_BY_EXECUTION_ID.$": "$$.Execution.Id"
        }
      },
      "End": true
    }
  }
}

```


# 呼び出したステートマシンが失敗した場合

以下のようなステートマシンを呼び出し、呼び出された側のステートマシンが失敗したときの呼び出し元ステートマシンの挙動を調べてみる。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1675618/19f25d48-e69b-0e2e-15f2-0a7a7f48106a.png)



```

{
  "Comment": "A description of my state machine",
  "StartAt": "Wait",
  "States": {
    "Wait": {
      "Type": "Wait",
      "Seconds": 5,
      "Next": "Fail"
    },
    "Fail": {
      "Type": "Fail"
    }
  }
}

```

## 実行後

### 呼び出されたステートマシン

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1675618/2ee3effe-0a75-34b9-0890-90450309351b.png)

### 呼び出し元ステートマシン

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1675618/1ee5bd4a-208d-6f47-7bec-61ece5cc6a32.png)

実行結果より、呼び出されたステートマシンが失敗すると、呼び出し元ステートマシンもそれに伴って失敗することがわかる。


# 並列に2つのステートマシンを呼び出し、一方が失敗した場合

次に、上で呼び出したステートマシンに加えて、以下のようなステートマシンを並列に呼び出し、一方が失敗した場合、もう一方のステートマシンと呼び出し元ステートマシンの挙動を調査してみる。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1675618/ffb9af0f-9b14-d0e0-9fab-8bec6dda4ba9.png)


```

{
  "Comment": "A description of my state machine",
  "StartAt": "Wait",
  "States": {
    "Wait": {
      "Type": "Wait",
      "Seconds": 30,
      "End": true
    }
  }
}

```

### 呼び出し元ステートマシン構成

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1675618/74c2436f-4aa7-a661-43b2-cbdfd15d7d75.png)


```

{
  "Comment": "A description of my state machine",
  "StartAt": "Parallel",
  "States": {
    "Parallel": {
      "Type": "Parallel",
      "End": true,
      "Branches": [
        {
          "StartAt": "test1",
          "States": {
            "test1": {
              "Type": "Task",
              "Resource": "arn:aws:states:::states:startExecution.sync:2",
              "Parameters": {
                "StateMachineArn": "arn:aws:states:{Region}:{AccountID}:stateMachine:{StateMachineName}",
                "Input": {
                  "AWS_STEP_FUNCTIONS_STARTED_BY_EXECUTION_ID.$": "$$.Execution.Id"
                }
              },
              "End": true
            }
          }
        },
        {
          "StartAt": "test2",
          "States": {
            "test2": {
              "Type": "Task",
              "Resource": "arn:aws:states:::states:startExecution.sync:2",
              "Parameters": {
                "StateMachineArn": "arn:aws:states:{Region}:{AccountID}:stateMachine:{StateMachineName}",
                "Input": {
                  "AWS_STEP_FUNCTIONS_STARTED_BY_EXECUTION_ID.$": "$$.Execution.Id"
                }
              },
              "End": true
            }
          }
        }
      ]
    }
  }
}

```

### 呼び出されたステートマシン（意図的に失敗させた方）

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1675618/31ff3d49-7294-a95d-bbb5-d594f7891534.png)


### もう一方の呼び出されたステートマシン

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1675618/bc04eb93-23fc-bbaa-10fa-4f223aaede08.png)


### 呼び出し元ステートマシン

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1675618/1ede9ce5-1bf1-a90e-96de-fb2fa13b872d.png)


実行結果より、呼び出されたステートマシンが1つでも失敗してしまうと、他の呼び出されたステートマシンは実行がキャンセルされてしまい、呼び出し元ステートマシンも失敗扱いとなってしまうようである。

# まとめ

ステートマシンを同期的に呼び出した際、1つのステートマシンが失敗してしまうと、他の呼び出されたステートマシンや呼び出し元ステートマシンの実行も中断されてしまうため、注意が必要である。
これらを回避するためには、同期的に呼び出すのではなく、非同期的に呼び出す（コールバックを待つなど）のが賢明でありそう。