fix(dispatch): run scheduled_actions + spawn_requests on the inline integration path (ARN-188)#349
fix(dispatch): run scheduled_actions + spawn_requests on the inline integration path (ARN-188)#349rita-aga wants to merge 1 commit into
Conversation
…ath (ARN-188) When await_integration=true and a transition's custom effect maps to an inline WASM/adapter integration that returns a callback response, run_post_dispatch_effects early-returned that callback response before dispatching the ORIGINAL transition's spawn_requests and scheduled_actions. Those effect lists belong to the original transition (the callback is a separate action), so the original transition's child-entity spawns and scheduled timers were silently dropped. The path is reachable in production via OData ?await_integration=true. Extract the spawn + scheduled dispatch into a shared helper dispatch_transition_deferred_effects and invoke it on both the normal path and the inline early-return path, so the original transition's deferred effects always run before returning the integration-updated response. Steps 5b (platform hooks), 7b (state-timeout arming) and 8 (query projection) stay owned by the callback's own dispatch on the inline path: re-running 7b on the stale intermediate state would arm a superseding wrong-state timer, and 8 is sequence-guarded. Adds a red-green regression test: a transition emitting a custom_effect (inline adapter callback) plus a schedule and a spawn, dispatched with await_integration=true, now observes the scheduled action fire and the child entity spawn. Co-Authored-By: Claude Opus 4.8 <[email protected]>
|
@greptile review |
There was a problem hiding this comment.
rita-aga has reached the 50-credit limit for trial accounts. To continue receiving code reviews, upgrade your plan.
There was a problem hiding this comment.
rita-aga has reached the 50-credit limit for trial accounts. To continue receiving code reviews, upgrade your plan.
ARN-165 principle audit — request changesMoving scheduled/spawn effect handling before one early return fixes the reported local reproduction, but it does not fix the durability root. Blocking findings
Required directionRepresent timer/spawn/cross-entity work as durable intents co-committed with the accepted transition. Claim them with leases/idempotency keys, retry with classified backoff, and recover after restart. Add deterministic crash points before/after parent commit, claim, child dispatch, and acknowledgment. Please keep the control-flow fix as a regression test, but move responsibility out of the inline branch. The current PR is a surface repair and should not close ARN-188. |
Closes ARN-188 (High, Bug) under epic ARN-165. Draft for review — do not merge.
Bug
run_post_dispatch_effects(dispatch/effects.rs): whenawait_integration=trueand a transition's custom effect maps to an inline WASM/adapter integration returning a callback response, the code returned before the spawn_requests + scheduled_actions steps. Those belong to the original transition (the callback is a separate action), so the original transition's child-entity spawns and scheduled timers were silently dropped. Reachable in prod via OData?await_integration=true.Fix
Extracted the deferred-effects steps into a shared
dispatch_transition_deferred_effects, called on both the normal path and the inline early-return path, so the original transition's spawns + scheduled actions always run. Deliberately did not re-run steps 5b/7b/8 on the inline path — the callback already armed the final-state timer, so re-running 7b on the stale intermediate state would arm a superseding wrong-state timer (a regression). Both reviewers confirmed this scoping.Red→green
inline_integration_still_runs_scheduled_and_spawn_effects: a Trigger transition emits a custom effect (→ inline http callback → Done) plus a scheduled Tick plus a spawn Child, underawait_integration=true. RED: parent stuck at Done (Tick dropped). GREEN: parent reaches Ticked, child Initialized. Scoped: adapter_dispatch 6/6, wasm_dispatch 6/6, --lib dispatch 102/102. Code review PASS + DST-READY (both genuine).🤖 Generated with Claude Code