How it works
Local-first. One daemon. Two doors.
Cairn is a single local daemon over a SQLite database in your home directory; your corpus never has to leave your machine.
Machines use the MCP server: any MCP client can search, read and write with provenance captured automatically.
Humans use the web app on localhost: library, review queue, diffs, analytics, audit.
Quickstart
Running in three commands.
git clone https://github.com/richardthedesigner/damllm.git cairn && cd cairn
npm install && npm start # web app on http://localhost:4800
claude mcp add --scope user cairn -- node $PWD/packages/mcp/dist/index.jsFull setup, including Claude Desktop registration and first capture, lives in the docs.
The contract
Nine tools, no magic.
The whole machine interface. Small enough to read, boring enough to trust.
search_assets
(query, filters?) → Asset[]
BM25 full-text over title, summary, content, tags. Defaults to the approved tier: the trusted, human-reviewed set.
get_asset
(id, version?) → Asset
Full content plus provenance. Current version by default, any version on request.
write_asset
(title, type, content, provenance) → draft
Capture with provenance. Always lands as a draft; a human promotes it. Near-duplicates are refused with a hint to version instead.
new_version
(id, content, note) → Asset
The right way to improve existing work. Immutable history, one canonical current.
diff_versions
(id, from, to) → patch
Unified diff between any two versions.
set_status
(id, status) → Asset
draft → review → approved → archived. Every transition is audited.
find_similar
(text) → matches
The duplicate guard, callable directly. Check before creating.
list_collections
() → Collection[]
The shape of the corpus: names and counts.
set_session_context
(chat, model, tool)
Call once per session so every subsequent write is traceable to its conversation.
No lock-in
Your corpus is a file you can leave with.
One click (or one API call) exports everything as portable JSON: content, versions, provenance, the lot. If Cairn stops earning its place, take your work and go. That promise is load-bearing.
GET /api/export → cairn-corpus.json # every asset, every version, all provenance