The Handoff Is the Unit of Design: Delegating to Agents Without Losing the System
Once agents write a meaningful share of the code, my output is no longer typed code — it is delegation decisions. These are my notes on the human discipline that makes that work: sizing every handoff to the review I can afford, the brief I hand over instead of big tasks, and the four habits that keep me connected to a system I am no longer typing into — from Bainbridge's 1983 ironies to a METR result that has since reversed its own sign.
When I wrote about Zero Token Architecture, the question was whether to call inference at all: every AI call is an architectural decision, and most of the cost sits outside the token meter. This post is about what happens after the answer is yes. Because once agents write a meaningful share of the code, my job description quietly changes — and I have watched the change happen at my own desk. The output of my working day is no longer typed code. It is a stream of delegation decisions: what to hand over, how much of it, with what constraints, and how I will know it came back right.
That is an architect's job, whether or not the title says so. And like any architecture, it can be done deliberately or by accident. The accidental version is familiar by now: a paragraph-long prompt describing a feature, twenty minutes of generation, a two-thousand-line diff, and a developer scrolling through it in the state I called "admiring" in the last post — impressed, nodding, not verifying. The deliberate version is a discipline, and the discipline has one load-bearing idea: the handoff, not the feature, is the unit of design.
Bainbridge described this seat in 1983
None of this is as new as the tooling makes it feel. In 1983 the cognitive psychologist Lisanne Bainbridge published "Ironies of Automation", five pages in Automatica on industrial process control that read today like a review of my terminal setup. Her central irony: the more you automate, the more the human's role shifts from doing the work to supervising the work — and supervision is a role humans are set up to fail at, precisely because the automation took away the practice that kept their skills sharp. The operator is left with two jobs: monitoring, which erodes vigilance, and the rare hard intervention, which now demands peak skill from someone who no longer exercises it daily.
Swap "operator" for "developer" and "control loop" for "coding agent" and both ironies land intact. If agents handle every routine change, the fluency I need for the hard 10 percent — the gnarly race condition, the migration that touches everything — is exactly the fluency that atrophies. And the monitoring problem is worse in software than in a control room, because a green test suite looks identical whether the change underneath is sound or subtly wrong.
There is also an uncomfortable data point on what unstructured supervision costs. METR's randomized trial from mid-2025 put 16 experienced open-source maintainers on 246 real issues in their own repositories — codebases they had worked on for years, averaging over a million lines. With AI tools allowed, they completed tasks 19 percent slower. They estimated afterward that the tools had made them 20 percent faster. I keep that 39-point gap between perception and measurement pinned next to the verify-versus-admire question from the last post, because it is the same finding wearing lab clothes: the feeling of delegation working is not evidence that it is.
Updated August 2026: the headline number has since moved, and this post would be dishonest without saying so. METR's February 2026 follow-up re-ran the design with 57 developers across 143 repositories and 800-plus tasks and got the opposite sign — an estimated 18 percent speedup among the returning developers from the original cohort, 4 percent among new recruits, both with confidence intervals wide enough to cross zero. METR discounts its own result, and the reason is itself worth sitting with: so many developers now decline to work without AI that the experiment is systematically missing the people and the tasks with the most to gain. So the slowdown is not the durable finding. The gap between what those developers measured and what they believed is, and no revision has touched it. The discipline below is my attempt to earn a speedup rather than feel one.
The handoff is the unit of design
A big handoff fails twice, once at each end of the loop.
It fails on the agent's side because vague, sprawling specifications degrade output quality in compounding ways. The practitioner writing I rate highest this year converges on the same shape from different directions. Addy Osmani's March essay on multi-agent coding argues for atomic, bounded tasks with explicit pass/fail criteria, plan approval before any implementation, and kill criteria for stuck work — his line that "the bottleneck is no longer generation. It's verification" is the whole economy of this post in eight words. Calvin French-Owen, writing up his own workflow in February, lands on externalized plans chunked into numbered stages precisely because agents degrade when a problem outgrows the context window — and because a plan that lives in a file survives the session that wrote it.
It fails on my side for a reason that predates agents by decades. The largest code review study I know of — SmartBear's, on a Cisco Systems team — found that defect discovery holds up when reviews stay in the 200-to-400-line range, at under 500 lines per hour, in sessions capped near an hour; push past that and detection collapses. Those numbers describe human attention reviewing human code, and applying them to agent output is an extrapolation, and I flag it as one. But the underlying constraint — my attention — did not change when the author did. If anything the numbers flatter the agent case, because agent code arrives without the shared context a colleague's change carries.
The industry data says that budget is already under pressure from the other side. As AI adoption rises, pull requests are running roughly 18 percent larger, while incidents per PR are up about 24 percent and change failure rates about 30 percent — more lines arriving per review, with the same pair of eyes. The OCaml maintainers made the shape of it public when they turned down a 13,000-line AI-generated pull request, not because the code was necessarily wrong but because nobody had the bandwidth to find out.
Put the two failure modes together and you get the sizing law I now design handoffs against: size the task upstream to the review you can afford downstream. Not "how much can the agent generate" — generation is nearly free. The question is how much I can verify with full attention in one sitting, and the honest answer has a ceiling of a few hundred lines. A handoff sized beyond my verification budget does not delegate the work; it delegates the responsibility, and silently. The moment the diff exceeds what I will actually read, I am no longer the orchestrator. I am a bystander with commit rights.
The brief I actually hand over
Sizing is necessary but not sufficient; a small vague task is still vague. What made delegation start working for me was treating the handoff document itself as the engineering artifact — the thing I craft with the care I used to spend on the code. My own practice, refined over months of daily use, is a plan-first structure: a master plan that captures the intent and sequencing, broken into small numbered child tasks with explicit dependencies, each child carrying its own status from pending through in-progress to completed or blocked. Nothing executes until I have reviewed the plan itself. That review — five minutes of reading before any code exists — is where I catch the architectural mistakes, when they still cost nothing to fix.
Each child task is a brief with the same skeleton:
## Task 03 — Extract retry policy into RetryPolicy type
**Depends on:** 01 (interfaces defined) · **Blocks:** 04, 05
**Scope**
Move the inline retry/backoff logic from `HttpSyncClient` into a
`RetryPolicy` value type. Touch only `sync/` — the callers in
`ingest/` are task 04, not this one.
**Constraints**
- No new dependencies.
- Public API of `HttpSyncClient` unchanged; this is internal.
- Follow the error taxonomy in `docs/errors.md` — do not invent
retryable/non-retryable classifications.
**Done means**
- `./gradlew :sync:test` passes, including the three new cases
named below.
- Diff stays under ~300 lines. If it will not, stop and report
why instead of continuing.
**Verify with**
- New tests: exhausted-budget path, jitter bounds, non-retryable
short-circuit.
- I will read the full diff before merge.
**Escalate when**
Blocked, or after 3 failed attempts at a passing build — do not
keep iterating past that.Every field earns its place by answering a specific failure I have hit. The scope boundary names what not to touch, because agents are eager and adjacent files are how a 300-line task becomes a 1,400-line diff. Constraints carry the decisions I refuse to delegate — dependency choices, public contracts, taxonomies — the "ideas, architecture, and project sequencing" layer French-Owen identifies as the part that stays human. The done-criteria are pass/fail, never "improve" or "clean up," and they include the diff budget itself as a stopping rule. The escalation clause encodes Osmani's kill criterion: an agent that has failed three times is generating entropy, not progress, and the brief says so in advance so that stopping is compliance rather than judgment.
The loop below is the whole system, and the thing to notice is where the two orange gates sit — both on my side of the desk, both before anything irreversible.
Staying connected without steering every line
The part of this discipline nobody's tooling solves is the one the question in my notes keeps circling: how to stay connected to a system I am no longer typing into. Bainbridge's answer for control rooms was deliberate, structured practice for the operators. Mine, translated to a codebase, is four habits.
The plan review is where control lives, not the code review. By the time a diff exists, the expensive decisions — boundaries, sequencing, what depends on what — are already made. Reading a five-line plan summary with full attention beats skimming a 900-line diff with the illusion of it. When I disagree with an agent's work, it is almost always the plan I should have disagreed with.
I read every merged diff, and I size the work so that stays true. This is the sizing law enforced socially rather than technically. The day I merge something I have not read is the day the mental model starts drifting from the code, and drift compounds quietly until an incident audits it for me. French-Owen, whose plan discipline I borrowed, has gone the other way — he spot-checks, holds the architecture in his head, and leans on Cursor's Bugbot and Codex review to catch what he no longer reads line by line. That is a defensible trade and I am not making it, because the reading is doing a second job for me that a review bot cannot do: it is what keeps my model of the system current.
The system's map lives in an artifact both the agent and I read. I keep an architecture description — component boundaries, allowed dependencies, the reasoning — in the repository, machine-checkable where possible. It serves double duty: the agent plans against it instead of guessing structure from package names, and writing it keeps the map in my head current. My Structurizr-and-ArchUnit setup from earlier this year turned out to be less about diagrams than about this: a shared source of truth for what the system is, that CI defends while I am looking elsewhere.
One task a week, I type myself. Deliberately, usually something routine I would otherwise delegate. This is Bainbridge's practice prescription applied to my own hands — the routine work is exactly what keeps the fluency that the rare hard intervention will demand. It costs me perhaps two hours a week. I think of it as paying the pension of my own judgment.
When delegation is the wrong tool
The discipline has honest limits, and the first one is the coordination floor. Even in METR's revised numbers the confidence intervals cross zero, which is a statistician's way of saying that on some tasks the overhead still eats the gain — and a brief is overhead. I do not write briefs for one-file fixes I can hold entirely in my head; by the time the brief exists, the change would have been typed. The handoff cost is real, and pretending otherwise is how orchestration becomes ceremony.
Design work where writing is the thinking also stays on my side. When I do not yet know what I want — a new bounded context, an unfamiliar protocol, anything where the first attempt exists to be thrown away — delegating the exploration means delegating the learning, and the learning is the deliverable. The agent gets the task after the shape is clear, not before.
And there is a fleet-size limit I respect even though the tooling no longer enforces one. Every parallel agent multiplies the review surface, and my verification budget is fixed. Two, occasionally three concurrent tasks is where I stop; past that, the gates queue up and the pressure to skim becomes structural. The constraint was never how many agents I can run. It was always how much finished work I can receive with my attention intact.
Takeaways
- The handoff is the unit of design. Size every delegated task to the review you can afford downstream — a few hundred lines, one sitting — not to what the agent can generate.
- Write the brief as the engineering artifact: scope with a "do not touch" boundary, pass/fail done-criteria, a diff budget as a stopping rule, and an escalation clause that makes giving up after three failed attempts the correct behavior.
- Review the plan before any code exists; that is where the decisions you must not delegate — dependencies, contracts, sequencing — actually get made.
- Keep the system's map in a shared artifact the agent plans against and CI enforces, and read every diff you merge.
- Type something routine yourself on a schedule. Supervision without practice is how the skill you will need for the hard intervention quietly disappears.
Reach for this discipline when the work decomposes into bounded, verifiable steps inside a system whose map you already hold. Skip it — and just write the code — when the task fits in your head, when writing is the thinking, or when the brief would outweigh the change. The last post argued that every inference call is an architectural decision. This one is the follow-through: every handoff is one too, and the architect who stops reviewing the building as it goes up has kept the title while giving up the job.
Still here? You might enjoy this.
Nothing close enough — try a different angle?
Related Posts
Engineering Before Inference: The Question Zero Token Architecture Is Actually Asking
Lately I keep hearing a sentence that would have been absurd three years ago: "I can't do it now — I ran out of tokens." These are my notes from digging into Zero Token Architecture — the idea Kelsey Hightower took from a throwaway post to a PlatformCon keynote — and the principle I want to build on it: every AI call is an architectural decision, and the costs that matter most were never the tokens.
Turning Repo Maintenance into Markdown: Keeping a Rust Codebase Alive with Agentic Workflows
Long-lived repositories drift: deprecated components linger, layers bleed, and tests miss the functions that actually break. In my own study I turned three recurring chores into scheduled markdown workflows the repo runs on itself, then wrote up what I learned about capping blast radius, pairing LLM checks with deterministic scans, and letting agents draft shapes while I write the substance.
Code Graphs for Coding Agents: The Delivery Shape Matters More Than the Algorithm
I spent a weekend pointing a coding agent at a 480k-line Go monorepo and watching it grep-loop through 38 tool calls on one question. AST-derived code graphs fix that, but the delivery shape — local stdio MCP, remote service, or skill — changes the economics more than the graph algorithm does. Here is where I would put one in 2026, with a minimal Go indexer I can drop next to the agent.