particle-academy/fancy-flow-php
Fancy Flow for PHP is a lightweight package for defining and running multi-step flows in Laravel apps. Express processes, transitions, and conditions in fluent PHP, with an API designed to stay simple, readable, and easy to test.
for_each executor and inline subgraph executor exist specifically so that per-item progress, per-item logs and per-item messages can be produced inside the graph rather than by looping inside one executor. Until v0.64.0 that promised value was silently undeliverable: nested runs forwarded only node-checkpoint and dropped node-status, node-message and log. Any roadmap item that assumes "users can watch each item in a batch progress" is only now actually buildable.RunEvent::forParent() is the kind of fix you get from a maintained dependency and rarely from a side project.each/0/body, each/1/body, …) rather than assume every node-status maps to a top-level node. That is a design decision you inherit: your dashboards should be keyed on address, not on event counts.Adopt when:
resume are first-class, not bolted on.node-status, node-message, log, node-checkpoint) to drive UI, alerting, or audit logs.Look elsewhere, or scope down, when:
run-start, run-end, run-error are deliberately not forwarded — a lane does not have its own lifecycle in the parent's stream. If your product needs per-item start/end notifications, derive them from node-status on the lane, or plan extra work.To executives: We are evaluating a Laravel workflow engine that runs long, multi-step jobs durably — if a job fails halfway, it resumes from where it stopped instead of starting over. The v0.64.0 release fixes a real defect: work split into per-item branches could report completion to the system but not to a human, so progress bars, per-item logs, and "what is it doing right now?" visibility were silently missing — while every durability test still passed. That is a support-cost and trust issue, and it is now fixed. The caveat is maturity: this is a 0.x package, iterating quickly, and we should treat the dependency as fast-moving rather than settled.
To engineering: No code changes are required to pick up the fix, with one exception — if any consumer counts node-status events or assumes they all refer to top-level nodes, it must be updated to key on the event address (each/0/body, each/1/body, …). You will now receive node-status, node-message and log from inside for_each lanes and subgraph runs; run-start/run-end/run-error remain intentionally un-forwarded so a workflow is not reported as starting once per item. The forwarding logic is now a single implementation, RunEvent::forParent(), shared by both executors — previously each executor carried its own copy, which is precisely how both came to be identically wrong. Worth flagging as a process gap: the durable-path tests were comprehensive and the human-facing-event path had no assertions at all. If we adopt, we should add coverage on the events our product actually renders.
How can I help you explore Laravel packages today?