Picture a support tool that only has to do three things: look up an order, check it against a refund rule, and reply. Give that job to a general purpose agent loop with a dozen tools and a system prompt telling it to “use good judgment,” and it will occasionally take four tool calls to do what one deterministic function could do. Every so often it will pick the wrong tool entirely, the same wrong tool selection failure I dug into in OpenAI Function Calling Feature. The task didn’t need an agent. It needed a workflow. Most teams don’t find that out until after they’ve already built the agent.
There is a clean way to draw the line between these two system types, and it’s the right first question to ask before writing any orchestration code: is this a workflow, a single agent, or does it need more than one agent talking to each other. Below is what that line actually is, five reusable workflow patterns, and what changes once subagents enter the picture, because the Claude Agent SDK and Claude Code implement all of this with specific, documented mechanics around context isolation that most explainers skip.
In this article:
The two categories split on control flow, not on how impressive the system looks. A workflow is a system where the LLM and its tools are orchestrated through code paths a person wrote in advance. An agent is a system where the LLM itself decides what to do next, in what order, and when it’s done, keeping control over how it accomplishes the task.
That’s the whole test. If a human wrote the sequence of steps in advance, call this, then that, then check this condition, it’s a workflow, even if every step inside it is an LLM call. If the model is deciding its own next action, it’s an agent, even if that agent is a single LLM call sitting in a while loop. A system can look sophisticated and still be a workflow.
This isn’t a hierarchy where agents are the advanced version and workflows are for beginners. The right posture is to start with simple prompts, optimize them with real testing and evaluation, and only reach for a complex agentic system once the simpler approach demonstrably falls short. A workflow that reliably does what you need it to do is not an unfinished agent.
Five workflow patterns cover most of what production systems need, and they’re not mutually exclusive. Real systems chain several of them together.
Notice what all five have in common: a human still decided the shape of the system. The LLM does the reasoning inside each box, but the boxes and arrows are fixed at design time.
Agents earn their complexity on a narrower set of problems than the current hype suggests. They’re built for open ended problems where it’s difficult or impossible to predict how many steps a task will take, and where you genuinely can’t hardcode a fixed path. A coding agent that has to explore an unfamiliar codebase, figure out what’s broken, and verify its own fix is a legitimate case for this, because nobody can specify in advance how many files it will need to read. I covered that territory from a different angle in AutoGPT: Empowering Automation and Beyond: autonomous loops are compelling exactly when the step count is unknowable up front, and unconvincing everywhere else.
That autonomy has a real cost structure, worth naming directly instead of hand waving. Letting a model direct its own steps raises both the bill and the odds of compounding errors, which is why sandboxed testing and explicit guardrails matter before shipping one. An agent that’s 95% reliable per step compounds that error rate across every step it decides to take on its own. That’s a different risk profile than a workflow, where the failure modes are enumerable in advance because the path itself is fixed.
This is also where the refund bot example from the opening earns its keep as a diagnostic question. If you can write down the steps right now, on paper, before the agent has run once, you already have a workflow. Building an agent for that task doesn’t add capability. It adds variance.
Orchestrator worker systems built with the Claude Agent SDK add a mechanic worth understanding on its own terms, because it’s an implementation detail of how Claude Code and the SDK actually run subagents: context isolation is the default, and it is not automatic in the way people assume.
Each subagent starts with a fresh, isolated context window by default. It doesn’t see the parent conversation’s history, the skills already invoked there, or the files already read. A subagent’s starting context is limited to its own system prompt, the delegation message the parent wrote when handing off the task, the project’s CLAUDE.md files, a git status snapshot, any skills explicitly preloaded into it, and a roster of its sibling agents. Nothing else carries over by default.
That’s a design decision with real consequences for orchestrator worker systems. If the coordinator needs a worker to have context from earlier in the conversation, that context has to be written into the delegation prompt explicitly. It doesn’t ride along for free. The one documented exception is a fork, a subagent that inherits the entire conversation so far instead of starting fresh, trading the isolation benefit for continuity when a side task genuinely needs the full history. The tradeoff runs both ways: a fork keeps its own tool calls out of the main context, since only the final result returns, but it gives up the clean room isolation that makes an ordinary subagent good for delegating side work you don’t want cluttering the primary thread.
This isn’t a minor implementation footnote. It’s the reason spinning up multiple agents is a bigger design decision than it sounds. A multi-agent system built on the assumption that workers share context with the coordinator will silently underperform a single well-structured agent, because each worker is reasoning from a fraction of what a human would think it knows.
Before reaching for either pattern, ask three questions in order.
First, can you write the sequence of steps down before running anything? If yes, it’s a workflow. Pick from the five patterns above based on whether the task is sequential (chaining), branching (routing), parallel (parallelization), unpredictable in scope but centrally coordinated (orchestrator workers), or in need of iterative refinement against a clear rubric (evaluator optimizer).
Second, if the steps genuinely can’t be predicted, does the task tolerate the compounding error risk that comes with letting the model decide its own path? If the failure mode is expensive or hard to detect, that argues for tighter guardrails or a hybrid, an agent operating inside a workflow’s outer structure, over pure autonomy.
Third, if the task needs more than one agent, have you written the delegation prompts as if the worker knows nothing beyond what’s on the page? If the design silently assumes shared memory between coordinator and worker, that assumption needs to become an explicit prompt field, or the system needs to use a fork instead of a fresh subagent.
None of this is about which system sounds more advanced. It’s about matching the control flow shape to the actual shape of the problem, and it’s still the cheapest lesson in this space to learn before writing code instead of after.
The Claude Certified Architect (Foundations) program groups this control flow distinction under its Agentic Architecture domain, one data point among the sources below rather than the basis for the framework above.
If you enjoyed the article and wish to show your support, make sure to: Workflows vs. Agents: A Decision Framework was originally published in Towards AI on Medium, where people are continuing the conversation by highlighting and responding to this story.