A library of decision records for Claude. Built to survive across sessions, so decisions do not have to be re-made — or worse, re-made differently.
When your agent doesn't know what to do, it should not guess and it should not re-derive: it should walk to the library and read what was decided before. Each shelf holds one domain. Every record carries a verdict, the evidence behind it, and a date — because verdicts age.
graph LR
source([source]) -- SETTLES --> topic[topic]
source -- DISPUTES --> source2([source])
probe([probe]) -- ABSENT --> topic
trap([trap]) -- VOIDS --> topic
trial([trial]) -- TAUGHT --> trap
new([new verdict]) -- SUPERSEDES --> old([old verdict])
cd bibliotech
.venv/bin/python bibliotech.py shelves # what is in the library
.venv/bin/python bibliotech.py open # what is still open
.venv/bin/python bibliotech.py status "<topic>" # is this settled? by what?
.venv/bin/python bibliotech.py traps "<topic>" # what would void the work
.venv/bin/python bibliotech.py near "<x>" 2 # 2-hop subgraph as triples
.venv/bin/python bibliotech.py stale 90 # what needs re-verifying
.venv/bin/python bibliotech.py lint # format problems, all at onceThe tool answers in Italian — it is a biblioteca, after all.
Before deciding anything that felt decided before, run status on it.
That is what this exists for.
Once, on a fresh clone (developed on Python 3.13):
uv venv && uv pip install -r requirements.txtor python3 -m venv .venv && .venv/bin/pip install -r requirements.txt.
Shelf and spine content is deliberately not committed — a fresh clone starts
with the structure empty. Grow your own.
The repo ships one tiny fictional shelf (coffee) in shelves/_example/.
Folders starting with _ are invisible to the tool, so it stays inert until
you copy it:
cp -r shelves/_example shelves/coffee
.venv/bin/python bibliotech.py shelves # the library is alive
.venv/bin/python bibliotech.py status "grinder choice" # settled — by what, and the house rule
.venv/bin/python bibliotech.py open # one verified absence
.venv/bin/python bibliotech.py search milk
rm -r shelves/coffee # it was never your libraryThen make it yours: mkdir shelves/<your-domain>, copy whichever _example
files you need as templates, and record the first thing you know — one
verdict that stands (with what settles it) and one absence you have actually
verified. Run bibliotech.py lint after editing: the parser warns about
malformed entries instead of guessing.
Your shelves are the one irreplaceable thing here, and git deliberately
ignores them — which means git is not protecting them either. backup.sh
mirrors your content (shelves, spine, counts) into a sibling repo with its own
history:
./backup.sh # mirrors into ~/Projects/bibliotech-content and commitsGive that repo a private remote and push it. Run the script whenever your content changes; it is idempotent and says "nothing new" when there is nothing new.
Markdown is the source of truth; you can read and edit it directly.
bibliotech.py parses it into a NetworkX multigraph. Nothing is generated
that you cannot also just open.
Predicates are a closed vocabulary, because decisions are taken from them — every verb carries an instruction, not a description:
| Edge | Instruction it carries |
|---|---|
SETTLES |
source → topic. Settled. Do not reopen without new evidence. |
ABSENT |
probe → topic. Verified missing, with the check that produced the null. |
VOIDS |
trap → topic. Ignore it and the work is void. |
DISPUTES |
source → source. Unresolved disagreement. Tread carefully, or dig here. |
TAUGHT |
trial → trap. We learned this the hard way. |
SUPERSEDES |
record → record. This verdict replaces that one. |
A shelf holds one domain: research areas, infrastructure choices, debugging lessons — anything where a verdict should outlive the session that reached it. The first shelf grown here was applied AI research; the shape is not specific to it.
Every absence carries checked and the exact check that produced the null.
An absence verified in July is not an absence in December. stale lists what
needs re-running. Re-run the check rather than trusting the record.
confidence: high means an API query returned zero or a listing was
enumerated. medium means many query variations found nothing, which is
weaker evidence. Either way, the verdict is only as wide as the corpora the
evidence names: "absent on arXiv" is not "absent". Write where you looked
into the evidence.
A shelf earns its place only when it has roughly ten records and answers a question that recurs. Below that it is a paragraph in a note, not a shelf — the known failure mode of this pattern is shelves proliferating until choosing one becomes its own problem.
A shelf is a directory under shelves/ with up to four built-in record
files — settled.md, absences.md, disputes.md, trials.md — all in the
same format:
## <record id>
- key: value
- key: value
free prose, kept as the record's detailMetadata lines must come before any prose, keys lowercase with hyphens.
checked: (an ISO date) is read everywhere — without it nothing ever shows
up in stale. supersedes: <record-id> is read in every record file except
disputes.md (a dispute is an edge between sources, not a record of its
own). The other keys per file: by: (settled.md, comma-separated source ids), title: /
topic: / confidence: (absences.md — put the re-runnable check in the
prose), between: A | B / about: (disputes.md), title: / path:
(trials.md).
Cross-domain facts go in the spine, not in a shelf: spine/traps.md
(title: / cite: / applies-to: — the topics the trap voids — and
learned-in: <trial-id>, which records that one of your own trials taught
you this, as a TAUGHT edge) and spine/sources.md (annotations for the
sources your verdicts cite: title:, url:).
A shelf may declare extra record types in a schema.md. Each section names a
new file, its kind, its predicate, and — mandatory — the instruction the
predicate carries:
## rules.md
- kind: rule
- predicate: GOVERNS
- instruction: follow these when working on the target topics
- targets-key: applies-toThe vocabulary stays closed; it is just closed per shelf. A predicate without an instruction is rejected: that would be a note, and this is not a note-taking system. The demo shelf ships exactly this example.
- Record it in
shelves/<shelf>/trials.mdwith an honest verdict — especially if negative; nobody will record your negative result for you. - If it taught you a trap, add it to
spine/traps.mdwithlearned-in: <trial-id>. - If it settled a topic (including your own idea), record that in
settled.md. If it overturns an old verdict, write the new record withsupersedes:instead of rewriting history. - Run
lint, run the test, updatecounts.json, run./backup.sh.
Libraries created before 2026-08 used research-flavoured names (closed.md,
closes:, gaps.md, area:, contradictions.md, experiments.md,
papers.md). One command converts a library in place, idempotently:
.venv/bin/python bibliotech.py migrateIn one session, Claude proposed two research directions that turned out to be already published — one had six competing accounts. The expensive part is not having ideas. It is knowing which ideas are dead. That became the first shelf; the library is the general habit: verdicts, recorded once, checked before acting, expiring on schedule.
MIT — see LICENSE.
