staleless document
Read the code, and say what documentation it would draft.
staleless document
Section titled “staleless document”npx staleless document --dryEveryone else generates documentation from a specification, so they can only describe what somebody already wrote down. This reads the code.
What is built today
Section titled “What is built today”--dry is shipped. It reads the repository, works out which pages it would
write, for which audience, from which files and lines, states what would be sent
and to whom, estimates the cost in tokens, and calls no model at all.
Warning
staleless document without --dry refuses, out loud, and says why. That
refusal is deliberate rather than a stub: a tool that invented pages would be
worse than one that says it cannot yet.
Because --dry needs no account and no token, it works on a repository that is
not a Staleless workspace at all.
--dryflagRead files, call no model, send nothing. The plan, for nothing.
--repo <dir>stringThe code to read. Defaults to the current folder.
--audienceinternal | customer | bothThey are different documents. See below.
--budget <n>numberA ceiling in tokens. Above it this refuses rather than spends.
document never answers 1. A plan is not a finding.
Two documents, not one with a flag
Section titled “Two documents, not one with a flag”| Audience | What it answers | Where it would land |
|---|---|---|
customer | How to call it, what to set, what each command does. | pages/api, pages/reference |
internal | What a module is responsible for, what it promises, what to do at three in the morning. | pages/internal |
Same source, different reader, different voice.
Nothing is read until you say so
Section titled “Nothing is read until you say so”A file in your own repository, .staleless/document.yaml, names the path
prefixes that may be read. It defaults to nothing, and a file that names nothing
is a refusal.
Four further limits:
Only what git tracks. That honours .gitignore exactly, and it is stronger
than .gitignore alone: an untracked scratch file holding a dumped production
response is not in .gitignore either, and is precisely the file nobody would
choose to send.
Never a credential. Files that hold credentials by convention are refused, and so is an ordinary source file with a key pasted into it. Every refusal is named in the output.
Said plainly before sending. --dry prints the file count, the byte count,
the token estimate, and who would receive it.
Cost is yours. The estimate is a token count, not money. What a token costs depends on the model a deployment names, and a price printed by a CLI would be a number it cannot know and you would believe.
Provenance is the point
Section titled “Provenance is the point”Every page it would write records the commit and the exact files and lines it came from:
---title: API endpointsgenerated_from: commit: cb5eddcacfd934578314204dce9a2cdddf6366bf files: - path: src/api/teams.ts lines: [1, 2]review_every: 90---When those files change, the page is marked for review. Documentation generated from code that knows when the code moved is the differentiator. Without the provenance it is a plausible page nobody can trust.
last_reviewed is deliberately absent. A machine that wrote a page has not
reviewed it.
Read and inferred
Section titled “Read and inferred”When drafting ships, two rules are enforced on the output rather than requested in the prompt:
Read. A fact taken from the source. It must carry the file:line it came
from, and the line must exist in what was sent. A citation to a file that was not
sent is a rejected draft, not a page with a bad link.
Inferred. Anything else, rendered as a visible marker in the page: “this endpoint appears to require authentication — unverified”. A page that says that is worth more than one that states it wrongly.
A draft with too much inferred and too little read is not staged at all. The job reports that the excerpts were too thin to write from.
It would never publish
Section titled “It would never publish”Output lands as a staged draft on a branch, exactly as the MCP write scopes do. A person opens the branch, reads it, and publishes it or does not.