The atom format
Everything in strands/ is plain markdown. Git is the source of truth; the CLI is one consumer of it. If the tool ever dies, the material is still readable and greppable.
A file
---
strand: countries
group: Europe / Nordic
tags: europe, nordic
---
Free prose before the first `###` is commentary and is ignored by the parser.
Use it to explain why a file is grouped the way it is.
### dk.capital
kind: capital
subject: Denmark
answer: Copenhagen
peg: A COPPER HEN roosting on a Danish pastry — copper-hen, Copenhagen.
peg_source: suggested
- Frontmatter between
---lines gives defaults inherited by every atom in the file. An atom may override any of them. - An atom starts at
### <id>. Ids are globally unique;lintenforces it. - Inside an atom,
key: value. A line that is neither blank nor a new key continues the previous value, so long answers can wrap. - A blank line ends a continuation.
Keys
| key | meaning |
|---|---|
kind | one of capital, flag, location, fact, contrast, causal |
subject | what the atom is about — supplies {subject} to templates, and is the default answer for reverse cards |
answer | required |
ask | overrides the kind's question template; required for fact, contrast and causal |
reverse | overrides the reverse template; reverse: none suppresses the reverse card |
reverse_answer | overrides subject as the reverse card's answer |
peg | the mnemonic image |
peg_source | suggested (written for you), own (yours), none (no image) |
tags | comma-separated |
note | shown during review, never tested |
source | provenance, if worth recording |
Atoms versus cards
An atom is a fact. A card is a directional recall test, and scheduling state is keyed per card, because knowing "capital of Denmark → Copenhagen" does not mean you know "Copenhagen → which country". Those decay separately and so they are scheduled separately.
cards_for() expands one atom into up to two cards: dk.capital (forward) and dk.capital~r (reverse).
Question templates
The files hold facts; the wording of questions lives in one place, TEMPLATES in akasha/parse.py:
| kind | forward | reverse |
|---|---|---|
capital | What is the capital of {subject}? | {answer} is the capital of which country? |
flag | Describe the flag of {subject}. | Which country flies this flag: {answer} |
location | Where is {subject}? Region, neighbours, coastline. | — |
fact / contrast / causal | explicit ask: required | — |
Rewording every capital question is therefore a one-line change, not a 147-file sweep.
Adding a kind
Add an entry to TEMPLATES. Use (None, None) if the kind always needs an explicit ask:. lint will then accept it.
Ids
Convention, not enforcement:
- countries:
<iso2>.<facet>—fr.capital,fr.flag,fr.loc - contrast sets: a descriptive slug —
nordic.crosses,slavic.tricolours - causal chains:
<chain>.<NN>.<slug>—rome.04.diocletian-split, so the chain sorts into its causal order
Ids are the scheduling key. Renaming an id orphans its review history — akasha prune will show you the orphan; there is deliberately no rename command, because silently moving a decade of review history is worse than making you think about it.