vault-doctor

A read-only Python script that checks the whole live vault in seconds — the checks that are exact and cheap as code but slow and fuzzy as LLM work. reconcile stays scoped to the weekly diff for judgment work; vault-doctor covers the mechanical whole-corpus checks reconcile explicitly doesn’t do.

When to use

  • As a reconcile step — run it, then interpret: which broken links intersect the week’s touched set (fix those), which are pre-existing (report count only).
  • After a refactor/move session — verify inbound links survived.
  • User asks “check vault health”, “find broken links”, “any orphan notes?“.

When NOT to use

  • Judgment calls (PARA fit, privacy classification, under-integration) — that’s reconcile.
  • Archived (5_Archive/) or generated (3_Resources/Japanese/) content — excluded from scanning by design; problems there are stale by definition.

How

From the vault root:

python3 7_Agent/skills/vault-doctor/vault-doctor.py

Prints a markdown report to stdout. Nothing is written to disk; the caller decides what to do with findings.

Checks

  1. Broken wikilinks[[target]] in a live note resolving to no note by basename, alias, or path. Resolution targets come from the whole vault (linking into the archive is legit); only live notes are scanned for problems. Folder links ([[5_Archive/]]), media embeds, and code blocks are ignored.
  2. Orphans — live notes with zero inbound wikilinks (capped at 50; 1_Home/, _index.md, Digest, Quotes exempt — they’re entry points or leaf collections).
  3. No frontmatter — info-level only: human-authored notes are exempt from the schema, so this is a census, not a violation list.
  4. Empty / near-empty — body under 10 chars.

Live scope = everything except 0_Inbox/, 5_Archive/, 7_Agent/, Templates/, 3_Resources/Japanese/, 6_Private/shinkansen-n2/.

Interpreting the output

  • Broken links intersecting this week’s touched set → fix directly (reconcile’s mechanical-fix license, see AGENTS.md).
  • Pre-existing broken links → report the count + worst offenders; fixing old prose links en masse is a user decision.
  • Orphans are a signal, not a defect — a fresh memo is often legitimately unlinked for a week. Rising orphan count in one folder is the interesting pattern.

Rules

  • Read-only. The script never edits; fixes go through whoever invoked it.
  • Don’t “fix” orphans by spraying links. Integration needs real conceptual connections — that’s the ingest/reconcile judgment work.

Verification

  • Exit code 0, report shows Live scope: N notes scanned with N in the hundreds.
  • No files modified (git status clean apart from what you were already editing).