Skip to content

Hand a spec to a coding agent

This guide shows you how to give a coding agent the build packet of a spec doc, and how to read its build reports.

A handoff is one record that a builder took the build packet of one version of a bundle. Speccy records the version and the verdict at that moment. Speccy never runs the build. The agent builds, and Speccy keeps the record.

  • The spec doc and every asset of the bundle, at the current version.
  • The spec doc of each bundle that this one links to, such as the PRD that an SDD implements.
  • Each external link, with its kind and its URL. A code target also carries the commit that the last run read.
  • The trace IDs that the doc defines, in document order.
  • The build questions of the newest full review, with the answer that the readers agreed on. A question that the readers read differently, or that the doc does not answer, carries no answer.
  • HANDOFF.md, the re-entry prompt.

The packet holds no findings and no review report. They describe the quality of the doc, and a builder builds from the doc itself.

The verdict must be Build Ready, and it must belong to the current version. Otherwise Speccy refuses the packet and says why: no review, a stale verdict, or the count of MUST findings to fix.

On a Build Ready doc with no handoff, the next action reads Hand it to a builder. On any doc, More → Hand it to a builder opens the same dialog.

  1. Click Hand it to a builder.

  2. Optional: in Label, name the work, such as a repo, a branch or a ticket.

  3. Click Download the build packet.

Speccy records the handoff and downloads a .zip file, such as payment-retries-v3-build-packet.zip. The .zip holds one folder with the files that speccy handoff --out writes. The History tab of the rail opens, and it lists the new handoff with its label.

When the verdict is not Build Ready, or is stale, the dialog says why. Download the build packet stays off until you select Take it anyway.

Under Copy for a coding agent, the dialog shows the speccy handoff command for this spec doc and a prompt that names the MCP tool handoff_bundle. Click Copy, and give the command or the prompt to the agent. The agent then takes the packet, and Speccy records that handoff. The command shows only in local mode, for a spec doc in the folder that Speccy serves.

Add Speccy as an MCP server that runs speccy mcp in the folder with your docs. In Claude Code:

Terminal window
claude mcp add speccy -- speccy mcp

speccy mcp serves the tools over stdio, as the local user. It uses .speccy/state/, so the app, the CLI and the agent share the same reviews, threads and handoffs.

MCP tools lists each tool and its input.

HANDOFF.md is the file an agent reads first, and again after it loses its context. It has five parts:

  • Read: the spec doc, its assets, the linked docs and the external links.
  • Answers: each build question with its agreed answer. A question with no agreed answer says to ask the author first.
  • Work: one unchecked line for each trace ID of the doc. A doc with no trace IDs asks the agent to write the list itself.
  • If you get stuck: the handoff ID, and how to send a build report.
  • Done when: every line ticked, and the project’s own checks pass.

The agent owns the file after the handoff, and it ticks the lines as it works. Speccy never reads it back.

A build report is what the agent tells Speccy about the doc. It names the handoff ID from the packet. It also names a section heading path or a trace ID, so the question lands on that text.

  • Blocked report: the agent cannot build a section without an answer. Speccy opens a blocking thread, and the bundle is Not Build Ready until a person resolves it.
  • Note: the agent built something, but the doc was unclear. Speccy opens an ordinary thread. A note changes no verdict.

The agent sends a report with the MCP tool report_build. A builder with no MCP connection uses the CLI:

Terminal window
speccy report docs/specs/refunds --handoff 3f0c2a8e-5b1d-4c7a-9e2f-6a4b8d1c0e97 --blocked --section "Refunds › Data model" --text "Which currency does a partial refund use?"

--section takes the heading path, with › between the headings. --trace-id REQ-012 names a trace ID instead. With neither, the thread anchors to the doc. Without --blocked, the report is a note.

  1. Open the Threads tab of the rail. The thread title names the kind of report, and the section or the trace ID it is about. A chip shows the version that the builder took.

  2. Answer in the thread. Change the doc when the answer belongs in it.

  3. Click Resolve. A resolved blocking thread no longer blocks, and the verdict returns to what the review found.

A report against a stale handoff never blocks. The doc changed after the builder took the packet, so the answer can be in the doc already. Speccy opens the report as a note, and the thread says so.

History lists each handoff, newest first: the label or the version, who took it, and the verdict at that moment. A handoff reads Current until the bundle gets a new version. It then reads Stale, and it names the version the bundle is at now. That tells an author that an edit landed after someone started to build.

History: the versions of the bundle, and the handoffs a builder took

Insights shows the false-ready rate of each profile under False ready. It is the share of the handoffs taken at Build Ready that came back with a blocked report. A handoff taken with acknowledged does not count. Sections that blocked a builder lists the sections that the blocked reports name, most frequent first. A high rate means the profile passes docs that a builder cannot build from.