feat(stepfunctions): add execution lifecycle with Pass/Succeed/Fail interpreter#241
Conversation
…nterpreter - StartExecution, StopExecution, DescribeExecution, ListExecutions, GetExecutionHistory, DescribeStateMachineForExecution - ASL interpreter with Pass, Succeed, and Fail state types - InputPath/ResultPath/OutputPath processing with simple JsonPath - Async execution via tokio::spawn with history event recording - 12 new E2E tests (25 total), 6 new conformance tests (14 total) - 15 unit tests for interpreter and I/O processing
There was a problem hiding this comment.
4 issues found across 8 files
Prompt for AI agents (unresolved issues)
Check if these issues are valid — if so, understand the root cause of each and fix them. If appropriate, use sub-agents to investigate and fix each issue separately.
<file name="crates/fakecloud-stepfunctions/src/service.rs">
<violation number="1" location="crates/fakecloud-stepfunctions/src/service.rs:395">
P1: Stopped executions can be overwritten by the background interpreter and end up SUCCEEDED/FAILED instead of ABORTED.</violation>
</file>
<file name="crates/fakecloud-stepfunctions/src/io_processing.rs">
<violation number="1" location="crates/fakecloud-stepfunctions/src/io_processing.rs:88">
P1: Avoid unwrapping `get_mut` in path traversal; non-object intermediates can cause a panic.</violation>
<violation number="2" location="crates/fakecloud-stepfunctions/src/io_processing.rs:105">
P1: Guard bracket parsing before slicing to prevent panics on malformed path segments.</violation>
</file>
<file name="crates/fakecloud-stepfunctions/src/interpreter.rs">
<violation number="1" location="crates/fakecloud-stepfunctions/src/interpreter.rs:248">
P1: JSON `null` paths (e.g. `"InputPath": null`) are never detected. `Value::Null.as_str()` returns `None`, so `== Some("null")` never matches. This silently breaks `ResultPath: null` (result replaces input instead of being discarded) and `InputPath/OutputPath: null` (input passes through instead of becoming `{}`).
Check for JSON null on the `Value` directly before extracting the string:</violation>
</file>
Reply with feedback, questions, or to request a fix. Tag @cubic-dev-ai to re-run a review.
| } | ||
|
|
||
| let now = Utc::now(); | ||
| exec.status = ExecutionStatus::Aborted; |
There was a problem hiding this comment.
P1: Stopped executions can be overwritten by the background interpreter and end up SUCCEEDED/FAILED instead of ABORTED.
Prompt for AI agents
Check if this issue is valid — if so, understand the root cause and fix it. At crates/fakecloud-stepfunctions/src/service.rs, line 395:
<comment>Stopped executions can be overwritten by the background interpreter and end up SUCCEEDED/FAILED instead of ABORTED.</comment>
<file context>
@@ -261,6 +277,276 @@ impl StepFunctionsService {
+ }
+
+ let now = Utc::now();
+ exec.status = ExecutionStatus::Aborted;
+ exec.stop_date = Some(now);
+ exec.error = error;
</file context>
| for part in path.split('.') { | ||
| if let Some(bracket_pos) = part.find('[') { | ||
| let name = &part[..bracket_pos]; | ||
| let idx_str = &part[bracket_pos + 1..part.len() - 1]; |
There was a problem hiding this comment.
P1: Guard bracket parsing before slicing to prevent panics on malformed path segments.
Prompt for AI agents
Check if this issue is valid — if so, understand the root cause and fix it. At crates/fakecloud-stepfunctions/src/io_processing.rs, line 105:
<comment>Guard bracket parsing before slicing to prevent panics on malformed path segments.</comment>
<file context>
@@ -0,0 +1,193 @@
+ for part in path.split('.') {
+ if let Some(bracket_pos) = part.find('[') {
+ let name = &part[..bracket_pos];
+ let idx_str = &part[bracket_pos + 1..part.len() - 1];
+ if let Ok(idx) = idx_str.parse::<usize>() {
+ segments.push(PathSegment::Index(name, idx));
</file context>
| obj.insert(segment.to_string(), serde_json::json!({})); | ||
| } | ||
| } | ||
| current = current.get_mut(*segment).unwrap(); |
There was a problem hiding this comment.
P1: Avoid unwrapping get_mut in path traversal; non-object intermediates can cause a panic.
Prompt for AI agents
Check if this issue is valid — if so, understand the root cause and fix it. At crates/fakecloud-stepfunctions/src/io_processing.rs, line 88:
<comment>Avoid unwrapping `get_mut` in path traversal; non-object intermediates can cause a panic.</comment>
<file context>
@@ -0,0 +1,193 @@
+ obj.insert(segment.to_string(), serde_json::json!({}));
+ }
+ }
+ current = current.get_mut(*segment).unwrap();
+ }
+ }
</file context>
| current = current.get_mut(*segment).unwrap(); | |
| current = match current.get_mut(*segment) { | |
| Some(v) => v, | |
| None => return result, | |
| }; |
| let output_path = state_def["OutputPath"].as_str(); | ||
|
|
||
| // Step 1: Apply InputPath | ||
| let effective_input = if input_path == Some("null") { |
There was a problem hiding this comment.
P1: JSON null paths (e.g. "InputPath": null) are never detected. Value::Null.as_str() returns None, so == Some("null") never matches. This silently breaks ResultPath: null (result replaces input instead of being discarded) and InputPath/OutputPath: null (input passes through instead of becoming {}).
Check for JSON null on the Value directly before extracting the string:
Prompt for AI agents
Check if this issue is valid — if so, understand the root cause and fix it. At crates/fakecloud-stepfunctions/src/interpreter.rs, line 248:
<comment>JSON `null` paths (e.g. `"InputPath": null`) are never detected. `Value::Null.as_str()` returns `None`, so `== Some("null")` never matches. This silently breaks `ResultPath: null` (result replaces input instead of being discarded) and `InputPath/OutputPath: null` (input passes through instead of becoming `{}`).
Check for JSON null on the `Value` directly before extracting the string:</comment>
<file context>
@@ -0,0 +1,561 @@
+ let output_path = state_def["OutputPath"].as_str();
+
+ // Step 1: Apply InputPath
+ let effective_input = if input_path == Some("null") {
+ json!({})
+ } else {
</file context>
Summary
tokio::spawn— StartExecution returns immediately, interpreter runs in backgroundTest plan
cargo clippy --workspace --all-targets -- -D warningscleanSummary by cubic
Adds a Step Functions execution lifecycle with an async interpreter for Pass, Succeed, and Fail states, including path processing and execution history. Exposes execution APIs so state machines can run end to end.
New Features
tokio::spawn; StartExecution returns immediatelyDependencies
tokiotocrates/fakecloud-stepfunctionsWritten for commit f9982f1. Summary will update on new commits.