Step a paused flow, and deliver what a rate limit held back
Three things a pause and an interval were quietly losing:
- A rebuild builds a fresh pipeline, so nothing is paused any more and no
resume ever comes for what the old one parked. Release it on rebuild.
- POST /flows/{name}/step takes the oldest parked item and runs that one wave
while the flow stays paused, so a held-back cascade can be walked through.
Nothing parked answers plainly rather than failing.
- A per-port interval was leading-edge only: a producer going quiet inside the
window left the consumer on the value before it. The held value is kept and
a flush item scheduled on the queue's existing timer, so the window ends with
a delivery. One timer in flight per node, and none without a queue to run it.
Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01H7LwYgJfpkbLCTeiAf8U4A
This commit is contained in:
@@ -541,6 +541,16 @@ async def resume_flow(name: str, controller: FlowControllerDep) -> Any:
|
||||
return Message(message=f"Resumed flow '{name}'")
|
||||
|
||||
|
||||
@router.post("/{name}/step", response_model=Message)
|
||||
async def step_flow(name: str, controller: FlowControllerDep) -> Any:
|
||||
"""Run one message a pause is holding back, leaving the flow paused."""
|
||||
_read_flow(controller, name)
|
||||
node = await run_in_threadpool(controller.step_flow, name)
|
||||
if node is None:
|
||||
return Message(message=f"Nothing held back in flow '{name}'")
|
||||
return Message(message=f"Stepped '{node}'")
|
||||
|
||||
|
||||
# -----------------------------------------------------------------------------
|
||||
# Validation and execution
|
||||
# -----------------------------------------------------------------------------
|
||||
|
||||
Reference in New Issue
Block a user