Graph Engineering Was a Joke. Deciding Which Cycles Matter Is Not.
Javier Perez, Founder · 2026-08-24
On 18 July 2026, Peter Steinberger asked on X: "Are we still talking loops or did we shift to graphs yet?" It was a joke about how quickly our field renames the same discipline. Hours later Hamel Husain published a piece titled Loop Engineering Is Dead. Enter Graph Engineering. That was a joke too. By the end of the week there were courses, roadmaps, and tool stacks. We have some skin in this: we wrote about loop engineering in June — citing Steinberger, taking him entirely seriously — and shipped Loops in July. So when the man whose slogan we built on turns around and needles the whole vocabulary, it seems worth asking what, if anything, is actually underneath.
Our answer is that the naming is silly and the problem is real, but the interesting question is neither graph nor loop. It is this: which cycles in software development deserve to be made explicit, and which ones are we currently flattening into a single agent loop and hoping for the best? That is the question ClusterCode Workflows exists to answer. We want to be precise up front about its status: Workflows is in Beta today. It is going to ship and it is going to be generally available; Beta means the core flow is solid and the surface is still moving, not that we are hedging on whether it lands. This piece is how we are building it and why.
It helps to notice how short the renaming chain actually is. Prompt engineering became context engineering became harness engineering became loop engineering became graph engineering, in about four years, and the last two transitions took six weeks between them. Turing Post traced the same 24 hours in Is Graph Engineering Real? and reached the honest verdict: "None of this is new to software engineering. State machines, DAGs, workflow engines, and orchestration systems have been doing versions of it for decades."
The prior art is not subtle either. LangGraph shipped in January 2024 for exactly this purpose, and its own announcement is candid about the shape: LangChain's chains "are directed acyclic graphs (DAGs)", they "lacked a method for easily introducing cycles", and the fix was to model agent runtimes as what the team "internally refer to as state machines". Microsoft's AutoGen paper had multi-agent conversation patterns in August 2023. And Anthropic drew the distinction the discourse keeps rediscovering back in December 2024, in Building Effective Agents: workflows are "systems where LLMs and tools are orchestrated through predefined code paths", while agents are "systems where LLMs dynamically direct their own processes and tool usage, maintaining control over how they accomplish tasks". The vocabulary was sitting there the whole time.
What genuinely changed in 2026 is not the diagram. It is that coding agents now take on multi-file, multi-hour work on real repositories, and a single loop doing all of it drifts. Anthropic's write-up on their multi-agent research system names the failure mode exactly: "Agents are stateful and errors compound... one step failing can cause agents to explore entirely different trajectories, leading to unpredictable outcomes." The same piece is refreshingly unromantic about where fanning out helps — "most coding tasks involve fewer truly parallelizable tasks than research, and LLM agents are not yet great at coordinating and delegating to other agents" — which is why our answer is not "spawn more agents". It is to draw fewer, better-bounded ones and let deterministic code own the routing between them.
The piece we most want to argue with is Boris Tane's The Software Development Lifecycle Is Dead, published in February, and named as the inspiration in our own Workflows design document — so we owe it an accurate reading. His claim is not that the lifecycle is slow. It is that agents killed it: the sequential stages existed to manage handoffs that no longer exist, and what replaces them is a tight loop he states as "Intent. Build. Observe. Repeat. No tickets. No sprints. No story points. No PRs sitting in a queue." He is bluntest about review — "The pull request flow needs to go" — and the arithmetic behind it is hard to dismiss: "An agent generates 500 PRs a day. Your team can review maybe 10." His one survivor is observability: "Monitoring is the only stage of the SDLC that survives."
We agree with more of that than we disagree with. The human review queue is a genuine bottleneck and it does not scale by adding reviewers. Verification has to be machine-driven and continuous. Intent, build, observe is the right inner loop, and we shipped a whole feature around it. Where we part company is the word dead. Compression is not death. Every stage he removes is still happening — it is just happening inside the agent's head, in one undifferentiated context window, with no boundary and no record. Which is another way of saying it now happens somewhere you cannot inspect, cannot gate, and cannot retry in isolation. That is precisely the compounding-error condition Anthropic describes: long-running state, one bad step redirecting the entire trajectory. The cure is not to put the stages back. It is fewer stages, each with an explicit boundary, so a failure is attributed to a node rather than to the whole run, and a retry re-enters at that node rather than at the beginning.
And on review specifically: we do not think the answer to five hundred pull requests and ten reviewers is to delete review. It is to make review a node — an adversarial one, with a machine-checkable verdict — and to keep a human gate only where the blast radius earns it. That is a design position, not a slogan, and it is what the primitives are shaped around. A ClusterCode workflow is a canvas-drawn graph with five node kinds, and each one exists because a specific cycle was worth naming. "Keep going until it is actually done" is a Loop node: a goal plus completion gates that are real shell commands with real exit codes, under an explicit budget of iterations, cost per iteration, daily cost, and wall clock. "Try it several ways and see" is a Prototype node, where up to six engine-and-model variants race the same brief, each in its own DevBox. "Is this good enough to proceed?" is a Decision node with labelled outgoing edges, exactly one of which is taken. "A person needs to look at this" is an Approval node, which sets the run to awaiting input and genuinely stops it, answerable from the run page or straight from the notification. And "go back and fix it" is a back-edge, which carries a maximum traversal count — three by default, twenty at the ceiling — so that iterate-until-done can never quietly mean forever.
Two constraints do a lot of the work. There is one active node at a time, a single token walking the graph, so the state you have to reason about is one attempt rather than a swarm. And a graph is capped at twenty nodes: if your lifecycle does not fit in twenty boxes, the boxes are wrong. But the most consequential choice on the canvas is smaller than any of that. A Decision node picks exactly one of three evaluators. The status evaluator reads the previous node's terminal outcome — a pure function, free, no container needed. The deterministic evaluator runs a command inside the run's DevBox and routes on the exit code: zero is pass, anything else is fail. The agent evaluator takes a judging turn with a forced structured tool call and persists its reasoning. The temptation is to reach for the agent evaluator everywhere, because it can answer anything, and that is the flattening mistake in miniature. If a command can settle it, a command should settle it. An exit code does not drift, does not cost tokens, and does not need to be re-read later to work out what it meant.
The graph validator enforces a surprising amount of this at draw time rather than at three in the morning. A deterministic decision whose edges are labelled yes and no is refused at save, because that evaluator can only ever emit pass, fail, or a default catch-all — labels a node can never produce would otherwise save happily and then fail on every single firing. A decision that can be reached with no DevBox is refused too, and the reachability analysis follows back-edges as well as forward ones, because a decision whose only inbound edge is a loop-back from a container-free node is still entered with no container at runtime. An approval's timeout branch has to match a real edge. Forward edges have to be acyclic, so a cycle you meant is a back-edge you have to mark, with a cap you have to choose. And one detail that is a design position rather than a bug fix: an approval's answer window has a floor of one hour, not five minutes. A gate is answered by a person who has to be notified, read it, and decide. A window that can lapse before the notification is opened is not a window.
Here is what that looks like on the lifecycle diagram Tane says is dead. Requirements is a Run node — read the repository, write it down once. System Design is a Prototype node, because design is where alternatives are worth racing rather than where one answer is worth committing to. Implementation is a Loop node, since it is the one stage that is inherently iterative, so it gets the iterative primitive and a budget. Testing is a Run node whose result becomes routable. Code Review is a Decision node using the agent evaluator, the one place a judgement call is genuinely unavoidable, and its "needs changes" branch is a back-edge into Implementation capped at two traversals. Deployment is an Approval node followed by a Run node, because nobody deploys unattended. And Monitoring is a Run node followed by a deterministic Decision — "is there an incident?" is a file check, an exit code rather than an opinion — whose pass branch is the return edge in the original diagram, re-entering Requirements and starting the cycle again. Ten nodes. Tane says monitoring is the only stage that survives; we agree, and we think that is exactly why it deserves to be a node that can route, rather than a dashboard somebody is supposed to be watching.
Now the honest accounting, because overclaiming here would be the easy mistake. What already exists: the primitives in that graph are not new to us. Loops and Prototypes ship today in ClusterCode, both in Beta, and a workflow's Loop node and Prototype node spawn those real features, each keeping its own detail page. Every node's work happens in a DevBox — an isolated, disposable environment we launch on a worker and throw away, not a worktree on somebody's laptop. A workflow run claims one DevBox and a branch and the graph walks inside it, while prototype variants each get their own. Secrets reach that container by injection and never enter a model's context; we published a case study earlier this year of agents delivering a feature across Jira, Confluence and Bitbucket using credentials they could only ever see as variable names, with a Codex review between a Claude plan and its implementation. That run predates Workflows. The graph is the generalisation of a shape we were already running by hand.
And what is not true yet: Workflows is unmerged and Beta-badged. The engine and the API surface are built; the canvas, the run pages and the schedule integration are being finished right now. Both of our browser test plans — the cheap all-kinds regression capture, and the full lifecycle-on-a-real-repository acceptance run described above — are written and have not yet been executed. Until that acceptance run passes, the graph above is a design we believe in rather than a result we have measured, and we would rather say so than let a blog post imply otherwise. We will write again when it flips.
It is also worth naming who else is here. LangGraph has offered cyclic, stateful agent graphs since January 2024 and is good at it; Temporal and Airflow have owned durable workflow execution for far longer. The distinction we care about is not the graph, which is table stakes and always was. It is what sits inside the nodes: a node here is not a function call, it is a full autonomous agent run, or a budgeted verification loop with a checker that did not write the code, or a race between engines — each landing in a disposable isolated environment on hardware you own, with real credentials it cannot read, each producing an entity with its own page you can open afterwards and inspect.
If you are drawing your first graph, five things we would tell you. Draw the boundaries where the failures are, not where the stages were — if you have never seen a stage fail on its own, it does not need to be a node. Prefer an exit code to an opinion, and reach for an agent verdict only when no command can settle the question. Put the human where the blast radius is rather than everywhere; one real approval gate beats five confirmation prompts nobody reads. Cap every back-edge and wire the give-up branch, because a loop with no exit is not iteration, it is a bill. And keep it under twenty nodes, because a graph you cannot hold in your head has replaced one opaque thing with a bigger opaque thing.
The lifecycle was never really about handoffs between teams. It was about naming the points where work should be checked before it continues. Agents removed the handoffs. They did not remove the checkpoints — they just moved them somewhere nobody can see. Graph engineering is a joke. Deciding which of your cycles deserves a name is not.
Run AI agents in isolated DevBoxes on machines you own.