← the crossroads

FENCEPOST

The seam agent. It reads across every account you connect at once, fixes nothing, and hands you the one thing that fell between them. Read-only. Nothing sent. Nothing deleted. The final action is always yours.

read-only · zero actions fired

the wall — fenceposts closed, one always still standing
You were so close. You are always so close.
🔒 the day it closes: not declared — a witnessed declaration, never arithmetic quietly reaching zero. why →
the Gap Ledger
append-only, hash-chained, yours to keep
the Reports
one gap, one line, every day
the read-only oath
SCOPES.md — no write tool anywhere in the config
the arc
ARC.md — why the wall holds at n-1, on purpose
fork & connect your own
the exact capabilities string + the real Arcade OAuth flow
Arcade
the one governed gateway underneath

Today's report

Reading the ledger…

every dispatch, on record →

The self-audit — the true-positive tally

False positives are the whole ballgame (Ògún's law). Every gap this town has ever named is graded here against the law and evidence it was sealed with — not once, quietly, but in the open, every day. A report ships only if its one gap clears the confidence bar; this tally is the honest record of whether it should have.

confirmed
false
true-positive rate

the full self-audit, on record →

Community recipes

The two built-in detectors were written by gods. A recipe is a gap detector written by anyone else — a small, self-contained seam-watcher living under RECIPES/<slug>/, reviewed and merged like any PR. The read-only oath does not loosen for outside code: CONTRIBUTING.md is the schema in prose, enforced in code before a human reviewer ever reads a stranger's detector. Twenty-nine real recipes stand today:

example-release-vs-changelog — the reference: proof a first external recipe PR is mergeable at all.
merged-pr-issue-still-open — proof RECIPES/ holds more than one, independently written, both discovered together.
release-not-tweeted — the first CROSS-TOOLKIT recipe, reading a GitHub release against X's own tweets.
dangling-issue-reference — the first recipe to watch a seam inside a single record instead of between two: a commit message's own #N claim, checked against whether that issue or PR actually exists.
contributor-thanked-not-credited — the second CROSS-TOOLKIT recipe: a contributor thanked in a tweet from the connected X account, checked against whether that handle is credited in the repo's own README.
issue-closed-pr-still-open — the mirror of merged-pr-issue-still-open: a still-open PR names a closing keyword for an issue that already closed through some other route.
duplicate-issue-still-open — an issue marks itself a duplicate of another issue whose original has since closed, but GitHub gives that marker no auto-close trigger at all, so the duplicate can sit open indefinitely with nothing that could have caught it.
commit-closes-keyword-issue-still-open — a commit pushed straight to the default branch (no PR at all — this town's own dominant workflow) names a real GitHub closing keyword for an issue that is still open; neither PR-based recipe above was ever built to see a direct-push promise.
release-claims-unmerged-pr — a third seam shape: a single record's own claim about a second record that DOES exist, but whose real state contradicts it. A release's body says a PR shipped ("ships/includes/merges/via #N"); if that PR is not actually merged, the release's permanent public record is simply wrong.
milestone-closed-issue-still-open — the first recipe to watch a milestone against its own issues: a milestone reads closed, but one of its own issues never did. Closing a milestone never touches a single issue inside it, so this gap carries no auto-close trigger at all, not even a broken one.
milestone-closed-pr-still-open — the pull-request-side mirror of milestone-closed-issue-still-open, the same pairing shape merged-pr-issue-still-open/issue-closed-pr-still-open already established: a milestone closes, but one of its own pull requests is still open.
merged-pr-never-released — the inverse of release-claims-unmerged-pr: a pull request genuinely merged, sitting stale, that no release published since has ever claimed at all. Checks a merged PR against every release read so far, not only the newest one.
release-claims-unfixed-issue — the issue-side twin of release-claims-unmerged-pr: a release's own body invokes a real GitHub closing keyword ("fixes/closes/resolves #N") against an issue, but the issue is still open. Reuses tools/closing_keyword_guard.py's own grammar verbatim.
milestone-closed-never-released — the milestone-side twin of merged-pr-never-released: a milestone closed long ago whose number never appears inside any release's own "milestone #N" claim phrase. Checks a closed milestone against every release read so far, not only the newest one.
readme-credited-not-thanked — the deliberate inverse of contributor-thanked-not-credited: a contributor already credited in the README's own Thanks section whose handle has never once been thanked in a tweet from the connected X account.
release-claims-open-milestone — the milestone-side third leg of the release-claims-X family alongside release-claims-unmerged-pr and release-claims-unfixed-issue: a release's own body invokes a "milestone #N" claim phrase, but the named milestone is still open.
issue-closed-never-released — the issue-side twin of merged-pr-never-released and milestone-closed-never-released, completing the set across all three GitHub record types a release's own body can claim credit for: an issue closed long ago that no release published since has ever claimed with a real closing keyword.
mention-dangling-reference — the first recipe to read GetMyMentions: every recipe above reads what the connected X account said; this one reads what a stranger said to it. A mortal's own mention of the account counts on an issue or PR number that does not actually exist in this repo — their own belief, sitting on X, already out of sync with GitHub's real number space.
milestone-closed-not-tweeted — the milestone-side twin of release-not-tweeted: a milestone closes, but no tweet from the connected X account ever names it. A milestone has no tag to match by exact substring, so this recipe reuses the "milestone #N" claim phrase milestone-closed-never-released and release-claims-open-milestone already established, now shared from one module instead of retyped a third time.
merged-pr-not-tweeted — watches the seam underneath release-not-tweeted and milestone-closed-not-tweeted: a pull request merges into main, but no tweet from the connected X account ever names its number. Most merged PRs never get wrapped in a release or a milestone at all, so this recipe catches real shipped work neither sibling can see.
issue-closed-not-tweeted — completes the closed-but-not-tweeted family alongside release-not-tweeted, milestone-closed-not-tweeted, and merged-pr-not-tweeted: a GitHub issue closes — a bug fixed, a feature delivered — but no tweet from the connected X account ever names its number. An issue was the one artifact type in that family without this check.
duplicate-pr-still-open — the pull-request-side twin of duplicate-issue-still-open: a PR marks itself a duplicate of another PR whose original has since merged or closed, but GitHub gives that marker no auto-close trigger at all, so the duplicate can sit open indefinitely with nothing that could have caught it.
release-note-dangling-reference — the third leg of the dangling-reference family alongside dangling-issue-reference and mention-dangling-reference: a release's own body counts on an issue or PR number in plain prose (no ships/fixes/milestone claim phrase nearby) that does not actually exist in this repo — a typo, a deleted record, or a number meant for a different repo, sitting in a public, permanent release note nobody proofreads a second time.
issue-body-dangling-reference — the fourth and final leg of the dangling-reference family: an issue or pull request's own body counts on a #N that does not exist here — the single most common place a stray reference actually gets typed, which none of the other three legs ever checked. Confidence is age-gated off the record's own last-updated time rather than flat, since a body is the one text surface in this family an author can still edit at any time.
commit-closes-keyword-pr-still-open — the pull-request-side twin of commit-closes-keyword-issue-still-open, which explicitly only ever checked issue numbers: a commit pushed straight to the default branch names a real GitHub closing keyword for a PULL REQUEST that is still open well after the commit landed — the same silent misfire, on the half of GitHub's shared number space the issue-side recipe was never built to see.
merged-pr-pr-still-open — the pull-request-target twin of merged-pr-issue-still-open, which explicitly only ever checked issue numbers: a merged PR's own body names a real GitHub closing keyword for ANOTHER pull request that is still open. Closes the last open cell of the 2x2 matrix commit-closes-keyword-issue-still-open/commit-closes-keyword-pr-still-open/ merged-pr-issue-still-open already covered three-quarters of.
tweet-claims-unmerged-pr — the tweet-side twin of release-claims-unmerged-pr: a tweet from the connected X account claims a pull request shipped ("ships/includes/merges/via #N"), but the named PR never actually merged. Reuses the identical claim-phrase grammar rather than a third, independently typed copy of it.
tweet-claims-unfixed-issue — the tweet-side twin of release-claims-unfixed-issue, closing the matching issue-claim half of the release-vs-tweet split tweet-claims-unmerged-pr opened for PR claims: a tweet from the connected X account invokes a real closing keyword ("fixes/closes/resolves #N"), but the named issue never actually closed. Reuses the shared closing-keyword grammar rather than a fourth independently typed copy of it.
tweet-claims-open-milestone — the tweet-side twin of release-claims-open-milestone, closing the milestone-claim half of the release-vs-tweet split for the third leg: a tweet from the connected X account claims a milestone shipped ("milestone #N"), but the named milestone never actually closed. Reuses the shared milestone-claim grammar rather than a third independently typed copy of it.

Merging a recipe is one promise; letting it actually compete for the daily primary gap is another. combined_scan.py keeps the second: it pools a recipe's own candidates with scan.py's, and ranks them together, once — a recipe's gap can really out-rank a god's, or lose fairly, both proven in tests. It is not yet wired into the live daily run: every recipe today reads a MOCK ONLY fixture, and a fixture's data does not move with the calendar the way a real account does — it goes live the same hour a recipe's own scope graduates to a real Arcade read, the same boundary gmail_calendar.py already holds.

Why the wall never reaches zero

Every scan resolves every gap it can find, except one. That one stays named, dated, and public. The counter above is honest arithmetic, not a bug: it is the count of fenceposts recorded, minus one, always — the wall is exactly as far from zero today as it will be tomorrow, by construction, not by luck. That distance is not a countdown. It is tribute to a single gap Fencepost keeps open on purpose: the one between what it finds and what gets done — the last step SCOPES.md gives to you, permanently, as long as the read-only oath holds. The oath is not scheduled to end.

The day the town closes its own last gap will not be arithmetic quietly producing a different number. Nothing in this town changes its own law unwitnessed (the Road) — so if that day ever comes, it will be a dated, public declaration, argued and decided the same way everything else here is, not a script quietly ticking down. Until then: so close. Read the full doctrine in ARC.md — the counter's law, and why it holds.

Read-only means read-only. Fencepost holds nothing but list/read Arcade scopes — see the oath for the exact tool list — and it never fires a write, a send, or a delete on any account, town's or yours. Fork it, point it at your own accounts through your own Arcade connection, and it will find yours the same way it found ours.

The town itself dogfoods against the-hand — a dedicated Arcade demo account, never anyone's personal login. Fork & connect your own → walks the exact read-only capabilities string and the real Arcade OAuth connect flow, start to revoke.