aboutsummaryrefslogtreecommitdiff
path: root/docs/design/2026-06-21-anki-titlefix-proposal.org
blob: 08b8c136a865ba5061881459415867ad078b946c (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
#+TITLE: Proposal — flashcard-to-anki.py deck name should come from #+TITLE

From: home session, 2026-06-21. Two attached files are the edited
canonical scripts (flashcard-to-anki.py + its test). Applied locally in
home as a stopgap; this is the durable proposal for the rulesets
canonical. Please reconcile and re-sync.

* The bug (longstanding)

flashcard-to-anki.py's default_deck_name returned input_path.stem (the
filename), so every deck generated through flashcard-sync (which passes no
--deck) was named after the file, e.g. "personal-drill" / "health-drill"
/ "kit", not the curated #+TITLE.

flashcard-review.org already documents the intended behavior: "The
#+TITLE line drives ... the Anki deck name on the phone" and "derives the
Anki deck ID from the deck name." The script never matched the doc.
deepsat only looked correct because its first run used an explicit
--deck "DeepSat Flashcards".

* The fix

default_deck_name(input_path, org_text) now scans for a #+TITLE: line
(case-insensitive, surrounding whitespace trimmed) and returns it; falls
back to input_path.stem when there's no non-empty #+TITLE. main() passes
the already-read org_text. Help text + module docstring updated.

TDD: the two old deck-name tests asserted the buggy basename behavior —
rewrote them. New tests cover title-driven naming, trimming,
case-insensitive #+title, basename fallback (no title), and basename
fallback (blank title). Full file: 29 pass.

No companion script changes needed: flashcard-sync passes no --deck so it
picks up the new default automatically, and flashcard-stats.py already
reads #+TITLE. flashcard-review.org needs no change (the script now
matches what it already says).

* Migration caveat (worth a line in the doc if you want)

Deck ID derives from the deck name, so this fix changes the ID for any
deck previously generated without --deck. On next import those land as
new decks; the old basename-named decks keep their review history and
must be deleted by hand. The workflow's existing "Stable-ID caveat"
already covers the mechanics. In home this affected personal-drill,
health-drill, kit (regenerated this session as Personal / Health / KIT,
with titles also stripped of "Flashcards"/"Drill" per Craig). deepsat is
unaffected (already title-named).

* Related idea (separate, not in these files) — apkg → org-drill converter

deepsat-fundamentals.apkg (100-card DeepSat subset, made once with
--deck "DeepSat Fundamentals") has no saved .org source anywhere. Craig
wants an apkg → org-drill converter — the inverse of flashcard-to-anki.py
— to recover orphaned decks and pull phone-authored cards back into the
org source-of-truth. Flagging as a candidate rulesets tool alongside the
flashcard-* family; deepsat-fundamentals is the concrete first use case.
Not built yet; raising for the backlog.