Why most KBs fail
Note-taking tools assume you'll do the writing. RAG stacks store chunks with no curation layer. Per-session memory tools live behind one agent and forget the next time you open a different project. Meanwhile, every decision, rejected library, and solved bug from your day is already captured somewhere — in your commits, your Claude Code transcripts, the URLs you text yourself. scribe is the daemon that turns that exhaust into a compiled, cross-project wiki.
How it works
Four input streams feed a two-pass extraction pipeline that writes
plain-markdown articles into a wiki you own. qmd indexes
the result for semantic search. Cron drives the whole loop.
01Capture
Four input streams, all running on cron with no human in the loop.
02Triage
BM25 keyword density scoring rejects boilerplate sessions before any LLM call. Cheap sessions cost nothing.
03Absorb
Two-pass extraction. Pass 1 grounds atomic facts; pass 2 fans dense sources out into multiple entity-first wiki pages — never one summary per source.
04Compile & index
Auto-generated wikilinks, backlinks JSON, retrieval-context paragraphs spliced into every article so semantic search catches implicit entities. qmd reindexes.
What makes scribe different
Four things that, taken together, no other tool in this neighborhood provides.
Claude Code becomes context-aware across sessions
scribe init writes a block into ~/.claude/CLAUDE.md that
tells Claude to query your KB via qmd's MCP server before
recommending a library, proposing an architecture, or reproducing a
pattern. No more re-explaining context every session. No more
Claude suggesting the library you already evaluated and rejected
six weeks ago.
Runs itself on cron
scribe cron install drops a set of macOS LaunchAgents (or
paste-ready crontab lines on Linux). Hourly auto-commits, 2-hourly
project extraction, 3×/day session mining, weekly Dream cycle for
consolidation. Set up once, then go back to your regular work.
Knowledge compounds across projects
Research, decisions, rejected tools, solved bugs, reusable patterns — all in one cross-project KB, not siloed per repo. Hit the same problem in project B that you solved in project A six weeks ago, and the old solution surfaces automatically.
Fully local-capable, zero API spend
Every pipeline stage — contextualize, atomic facts, pass-2 absorb —
can route through Ollama via the
new pass2_mode: json + pass2_provider: ollama knobs (v0.2.12).
scribe doctor --section localmode validates the setup before
you kick off a sync.
Plain markdown you own
The KB is a git repo of plain markdown files with YAML frontmatter. Push it to your own GitHub, Gitea, or Forgejo. Open it in Obsidian, VS Code, vim, or mdbook. Grep it with ripgrep. No vendor lock-in, no cloud account, no subscription. If scribe disappears tomorrow, you still have everything.
Typed graph, not just tags
Articles connect via typed edges — supersedes, contradicts,
specializes, derived_from, extends, and more.
scribe relations migrate uses an LLM to classify
existing related: links into the typed schema. Contradiction
and staleness ledgers nag you (gently) about KB hygiene.
Install in 60 seconds
macOS or Linux. Single binary. CGO + FTS5 baked in.
# Homebrew (macOS, Linux/Linuxbrew) $ brew tap oliver-kriska/scribe $ brew install oliver-kriska/scribe/scribe # Or shell installer $ curl -fsSL https://raw.githubusercontent.com/oliver-kriska/scribe/main/install.sh | bash # Bootstrap your KB $ scribe init --path ~/my-kb $ cd ~/my-kb $ scribe cron install → installed 14 LaunchAgents $ scribe doctor ✓ deps ✓ config ✓ cron ✓ freshness ✓ localmode
That's it. Cron will start populating the KB the next time you commit code, finish a Claude Code session, or text yourself a link.
What it actually feels like
Real loops from two weeks of the maintainer's normal use.
Evaluated a Go cron library for project A → two weeks later, started a different Go CLI
Claude Code automatically pulled the prior evaluation from the KB and skipped re-researching the alternatives. tools/quantum.md already had verdict: skip and the reason.
Hit an Oban worker idempotency bug → wrote the fix into wiki/patterns/idempotent-worker-skeleton.md
Three days later, different Phoenix project, same pattern surfaced without asking. qmd query "oban idempotency pattern" returns it from any directory.
Texted yourself a link about FTS5 MATCH syntax (not parameterizable)
Six weeks later, SQL-injection lint fired on a different project; the KB had the exact answer and the workaround. The bookmark went from your Messages thread to raw/articles/ to a wiki article without a single manual step.
Fixed a tricky LiveView reconnect loop with Claude Code at 3pm
By 3:30, scribe sync --sessions had mined the session via ccrider's FTS5 index, extracted root cause + fix + tradeoff into wiki/learnings/why-my-liveview-reconnect-loops.md, cross-linked it to wiki/patterns/phoenix-scope-based-auth.md, and auto-committed.
Run it locally for $0 v0.2.12+
Every LLM stage in the absorb pipeline can route through Ollama. No Anthropic key required.
# scribe.yaml absorb: contextualize: provider: ollama model: gemma3:4b # 3.3 GB, best speed/quality on Apple Silicon atomic_facts: true facts_provider: ollama facts_model: gemma3:4b pass2_mode: json # inlines a WikiActionEnvelope JSON prompt pass2_provider: ollama # scribe applies file mutations itself pass2_model: qwen2.5-coder:14b
$ scribe doctor --section localmode ✓ ollama daemon reachable at http://localhost:11434 ✓ pass-2 model qwen2.5-coder:14b is pulled ✓ atomic_facts is on (required for ollama pass-2 — prevents fact-ID fabrication) ✓ sync.daily_anthropic_output_token_ceiling configured (2,000,000) $ scribe sync → 3 projects extracted, 12 articles absorbed, 0 anthropic tokens used
scribe auto-pulls models on first use. Zero manual ollama pull needed.
Search from anywhere
qmd indexes the KB for semantic search; works from any
terminal in any directory.
$ qmd query "how did I solve the oban idempotency bug last quarter" wiki/patterns/idempotent-worker-skeleton.md (score 0.84) → use Oban.Pro Unique with :args fingerprint, fall back to advisory lock → linked from: 3 projects, 2 learnings wiki/learnings/oban-pro-uniqueness-trap.md (score 0.71) → :args hash collisions when payload contains floats $ qmd query "have I evaluated cron libraries for go" wiki/tools/robfig-cron.md verdict: use wiki/tools/quantum-erlang.md verdict: skip wiki/decisions/picked-robfig-cron-over-quantum.md 2026-04-09
How scribe compares
Snapshot 2026-04-21. Everything moves; check the source repos before deciding.
| Tool | Session mining | Cron-driven | Density pre-filter | Two-pass absorb | Multi-project | Local-mode |
|---|---|---|---|---|---|---|
| scribe | ✓ ccrider FTS5 | ✓ LaunchAgents | ✓ BM25 triage | ✓ fan-out | ✓ | ✓ Ollama / llama.cpp |
| claude-memory-compiler | every session, no filter | opportunistic | — ($115 / 20min, issue #3) | — | — | — |
| nvk/llm-wiki | — | one-shot /assess | n/a | — | — | — |
| basic-memory | — (issue #669 since Mar) | cron suggested | n/a | — | ✓ projects | — |
| RAG (LangChain, LlamaIndex) | — | indexing only | n/a | chunks only | ✓ | varies |
| Obsidian / Notion | manual | — | n/a | — | manual | n/a |
scribe is the wiki the LLM writes for you, sitting on top of raw sources kept verbatim. RAG retrieves chunks; scribe gives you a curated, named-entity wiki you can also grep.
— project README, "where scribe's niche is"The whole command surface
28 subcommands, all in one binary. Here are the ones you'll actually type.
$ scribe init # bootstrap a KB $ scribe sync # discover → extract → absorb → reindex $ scribe sync --sessions # mine Claude Code sessions $ scribe sync --estimate # token estimate, no LLM calls $ scribe capture # pull self-iMessaged URLs as bookmarks $ scribe ingest url# queue-less URL absorb $ scribe absorb <file> # absorb a local md/txt/html file $ scribe status # KB scoreboard $ scribe dream # weekly memory consolidation $ scribe relations migrate # LLM-classify related: into typed edges $ scribe contradictions list # unresolved factual disagreements $ scribe stale list # articles past their type's half-life $ scribe view active-decisions # declarative views over frontmatter $ scribe doctor # deps + config + cron + freshness $ scribe cost # claude -p USD estimate from cost ledger
Built on tools you probably already use
- ccrider — FTS5 index over Claude Code sessions; scribe runs BM25 against it for triage
- qmd — semantic search over markdown; scribe reindexes after every run, exposes via MCP
- Ollama / llama.cpp — local LLM runtime for the zero-API-spend path
- Claude Code — for the hot-path extraction calls (and as the consumer of the resulting KB via MCP)
- git — every KB is a plain git repo;
scribe commitauto-commits hourly
Get started
scribe is open-source, MIT-licensed, free to use. Built by a maintainer who's been running it on his own laptop for months.