Pick any page in your team’s wiki. Now answer this: is it still true?
You can’t, not without opening the code it describes and reading both. And if that page covers a service of any size, that’s twenty minutes. Multiply by two hundred pages and you have a task nobody will ever start, which is why nobody ever does.
This gets described as a discipline problem. Docs go stale because engineers don’t update them; engineers don’t update them because they’re busy; if the team just cared more, the wiki would be current. Every docs initiative I’ve watched starts from that premise, and every one of them dies about six weeks in.
I think the premise is wrong. It isn’t a discipline problem. It’s a missing-data problem.
The comparison that gives it away
We don’t ask whether the tests still pass. We run them.
Nobody sits down to read the test suite and reason about whether it still reflects the code, because the suite carries enough structure to answer that question mechanically. A test names what it exercises. A runner reports pass or fail. The question “is this still true?” has a command.
Documentation has no such command. A Markdown file is prose in a folder. It doesn’t declare what it’s about, so nothing can check whether what it’s about has changed. It doesn’t record when anyone last confirmed it, so you can’t even scope the problem to “pages nobody has looked at since March.”
That’s the actual gap. Not motivation — instrumentation.
What a checkable page needs
Surprisingly little, it turns out. Two facts:
What this page is about, expressed as paths rather than intent. Not “this documents the billing system” but packages/billing/**. A human phrase can’t be diffed; a glob can.
When it was last confirmed true, expressed as a commit rather than a date. “Updated March 2026” tells you nothing, because you don’t know what the code looked like in March. A SHA tells you exactly.
With both, the unanswerable question becomes a command:
git diff --name-only d70bf9ba..HEAD -- packages/billing/**
Empty output means nothing this page describes has changed since someone last verified it. That page is probably fine. Non-empty means the ground moved, and the page hasn’t been re-checked since.
So the frontmatter grows two fields:
---
title: The publish pipeline
sources:
- packages/publish-service/**
last_synced: "d70bf9ba"
---
That’s the whole mechanism. There’s no index to maintain, no service to run, no database. It’s plain YAML in a Markdown file, and it works with git, which you already have.
What this does and doesn’t tell you
I want to be precise here, because it would be easy to oversell.
A flagged page is not a wrong page. It means the files underneath it changed and nobody has re-confirmed the prose since. Maybe the change was a rename that invalidates nothing. Maybe it rewrote the behaviour the page describes. The signal doesn’t know which — it’s a smoke detector, not a verdict.
And an unflagged page is not a correct page. If someone wrote it wrong on day one, it’s been wrong ever since, and no amount of SHA-tracking notices. This catches drift, not error.
So what’s it actually worth?
It converts an unbounded question into a bounded one. “Which of our two hundred pages are lying?” has no answer anyone will pursue. “These six pages have changed underneath them since anyone checked” is a list. Lists get worked through. That’s the entire value proposition, and I’d rather state it plainly than dress it up.
There’s a second-order effect that took me longer to appreciate. Once staleness is visible, an old last_synced stops being embarrassing. A page that says “verified four months ago, nothing has changed since” is more trustworthy than an undated page, not less. Right now, age is invisible and everything looks equally current — which means everything is equally suspect.
The part that’s still hard
None of this writes the page. Something still has to read the changed files, work out what the prose got wrong, and fix it. That’s the expensive step, and the mechanism above does nothing about it.
What it does is make the expensive step targeted. You’re not auditing a wiki. You’re looking at six pages with a diff attached to each, which is small enough to be somebody’s Friday afternoon instead of a quarterly initiative nobody schedules.
That’s also the point where a coding agent becomes genuinely useful rather than a novelty — but that’s the next article.
The insight I’d want you to take away, whether or not you use my tool: documentation is the only artefact in your repository with no notion of whether it still holds. Tests have runners. Types have checkers. Dependencies have lockfiles. Prose has nothing — and it turns out you can fix that with two lines of YAML.