The deliverable stopped being a file and became a running app, on a branch that auto-deploys to the client's review site. This is the standard that makes that safe — branching, gates, two pull requests, deploy verification — and what it took for a five-person team to run it without me in the room.
$ diff local.txt deployed.txt (empty — the deploy is exactly the build)
A handoff file is a promise. The thing the client approved is a picture of the product, not the product — and every gap between the picture and the build gets discovered later, by somebody else, as a defect.
My team stopped making the picture. We design directly in code, in the client's repository, and the deliverable is a branch that builds and runs. The client reviews the actual thing. Nothing is lost in translation, because there is no translation.
That trade does not come free. It swaps the handoff problem for a sharper one: every habit a design team has is built around files. What counts as a review, when feedback is allowed, who may publish, what "done" means — all of it assumed the deliverable was inert. Ours now executes. A designer with merge rights, on a repo that deploys to a client, in US healthcare, is one habit away from publishing an accident.
So the real work was never the tool swap. It was writing down the process that makes the tool swap safe — and the rule underneath the whole thing came first: nothing is allowed to live only in someone's head. Not a decision, not a client correction, not the reason a feature was cut. If it is not in the thread, it did not happen.
The design branch auto-deploys to the client's review site. Which means: a merge is a publication.
Once that sentence is true, tidy code is the least of it. The standard has exactly two jobs beyond tidiness: make an accidental publication impossible, and make a bad deploy detectable rather than merely unlikely. Every rule in the document traces back to one of those two jobs — and the rules were not invented in advance.
Nothing here is theoretical. Every warning box is something that went wrong once and cost real time to find.
That line is from the standard's own preamble, and it is the honest description of how the document exists. It is a changelog of mistakes, organised so the next person does not have to repeat them.
The process is one continuous thread of context, from the first sales document to the dev handoff. It thickens every time something joins, changes carrier once, and never breaks.
The crossing is the fragile part. The chat and the code tool share no memory, so context crosses on .md files, by hand — CLAUDE.md, the project brief, the design system, the constants, the feature spec, plus the convention files that travel with the boilerplate. Into every repo, on the right branch. What is not written down does not make it across — which is not a weakness of the tooling so much as an enforcement mechanism for the no-heads rule above.
On the far side, the work happens in waves.
One feature, one branch, one commit, two pull requests. Ten steps, in order, and the order is the point.
And rather than describe what running one feels like — run one. The transcript is real: the commands, the gates, the deliberate stop, the publish warning, the hash check at the end.
While the dev branch lags, its PR shows a superset of waves. The standard's answer is unglamorous and correct: say so at the top of the PR body, name the merge order, and do not "fix" a cosmetic problem by stacking branches — that trades it for a real one.
Every instinct says a review is one thing: someone senior looks at the work, once, and blesses it. Applied to a coded design deliverable, that instinct quietly reviews the wrong thing at the wrong moment.
If the engineering review blocks the design branch, a comment about naming holds up a client demo. If the design review happens on the pull request diff, it reviews code — after the design has already settled, when changing it is expensive — and it reviews something a feedback round is about to rewrite anyway.
And underneath both: the person who faces the client and the person who takes the code to production are looking for different defects. Collapsing them into one review means one of them is skimming.
| The design review | The code review | |
|---|---|---|
| when | Steps 5–6 — before a commit exists | After the wave is pushed |
| against | The working tree, in a browser | The dev PR's diff |
| by | Whoever faces the client | The engineers taking it to production |
| asks | Is it the right thing? Is the copy true? | Architecture, reuse, naming, the mock seam |
| blocks | The commit | Nothing on the design branch |
The design review is the one that changes the product, and it happens while the work is still molten. The code review never blocks the client. Because the two are separated, neither is optional — skip the first and you ship the wrong thing quickly; skip the second and engineering inherits a deliverable nobody on their side has read.
The objection I get most: the designer is reviewing their own wave. The standard's answer, which I stand behind: the design is produced by a tool the designer is directing, so steps 5–6 are a review of that output — in a browser, against the specification — not someone marking their own homework. It is the same relationship any reviewer has with any author's work, compressed into one person and one sitting. And the feedback that arrives after a wave has shipped does not bend the rule: the dividing line is the commit, not the seniority of whoever spoke. Late feedback opens a fix/ branch and becomes the next wave, with its own review and its own deploy verification.
The standard's last section is titled "the rules that cost the most". These three earned their place.
The deploy workflow has run green while shipping the wrong build. So every merge ends with the ritual in the instrument above: build locally, list your content-hashed assets, list the deployed ones from the build log, diff — empty means the deploy is exactly the build. On one project the asset count went 8 → 12 → 14 → 17 → 21 → 19, and the rule is not "the count must not fall" — a bundler may legitimately merge chunks. The rule is an unexplained count is the only signal you get, in either direction.
Same family, worse disguise: hashed assets are cached forever, so the HTML shell must be synced separately with no-cache headers — or a returning reviewer gets yesterday's shell pointing at asset names that no longer exist. A blank page, on a site that deployed successfully.
A platform approval is pinned to a commit, and by default it survives new commits — so a pull request can show an approval for code nobody has read. One checkbox (dismiss stale approvals) is the difference between a review and the appearance of one, and it has to be switched on per repository, at setup.
The deeper version: requesting a review does not produce one. Whole waves were discussed in detail in chat while the pull-request record stayed empty. The standard's position is to stop pretending — decide which channel the ask actually goes through, and treat the platform record as bookkeeping unless audit needs it to be more. The habit changes deliberately, or it is not assumed to have changed.
A rule recorded in the design system has been cited to justify an exception — and never actually applied to the surface that needed it. Five blocked items once sat in a "do not start" table after the thing blocking them had been answered somewhere else. Interface copy described behaviour the product did not have, which is a defect where the fix is usually the missing behaviour, not softer words.
The standard's countermeasures are all small and procedural: audit against the specification rather than your own notes, re-read the blocked list whenever a decision lands, sweep the copy for capability claims, and treat seed data as copy — it is read by the same people and carries the same authority.
A standard one person follows is a habit. The test was whether it survived contact with four other designers, parallel waves, and a platform it was not written for.
Parallel work was designed in, not discovered. One branch per wave is what lets several designers run at once without colliding; the branch prefixes keep the history legible; the two-PR shape means nobody's client demo waits on anybody's code review.
The document knows what it does not know. Two things are deliberately blank — who holds the DevOps role on an engagement, and whether code review is a named person or the team — because those are organisational, and pretending they are technical would make the standard wrong somewhere. Each repository's own agent guide stays authoritative for its exact branch names, base paths and gate commands; the standard generalises them for starting the next project.
And it has already survived its first inversion. The mobile adaptation, written the same week, keeps the wave loop and the two-PR shape but flips the central rule: on mobile, publication is a build, not a merge — a binary someone installs cannot be un-shipped the way a deploy can be replaced. The adaptation records only what differs and why, down to "yarn, never npm" with the exact peer-dependency reason. A v1.0 that can absorb that inversion without rewriting its philosophy is the closest thing process work has to a passing test.
What I think is genuinely good: the one-thread rule, which makes the whole flow auditable; the two-review split; and the deploy-verification ritual, which converted "probably fine" into a thirty-second check with a yes/no answer.
What honestly limits it:
The paper trail, all of it mine to publish: the standard itself, v1.0 — seven pages, as the team runs it; the context-thread diagram above, drawn as the companion to the sprint-flow document; and the mobile adaptation quoted in section 07, which records the standard's first platform inversion. Client work stays unnamed throughout — the process is the publishable part, and it was written that way on purpose.
Screens are absent from this page by design: every screen this process has produced belongs to a client. The two case studies beside this one show the craft; this page shows the system that ships it.