kimal3 0.7.0 → 0.9.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -88,7 +88,12 @@ use them instead of starting off too quickly.
88
88
 
89
89
  ### 3.3 Planning, now concretely
90
90
  - What exactly is built, in which steps, how each step is checked. For bigger things in writing: a spec,
91
- that is a plan with user stories ("As … I want … so that …") and a counter-check per criterion.
91
+ that is a plan with user stories. Every story sits in four boxes, always in this order:
92
+ **User story** ("As … I want … so that …"; the title names the person's goal, not the result) ·
93
+ **Acceptance criterion** (four lines: *X has …* · *X does …* · *Then …must …* · *Counter-check: …* — a criterion that
94
+ cannot fail is none) · **How you test it** (numbered steps for someone without technical knowledge: where, what to do, what
95
+ appears; below them the line "Doesn't work if: …"; a command only with its place, in backticks) · **Technical note**
96
+ (where the thing lives, what carries it — the person need not read it). Real numbers, real text, a name instead of "the user".
92
97
  - **An approved plan justifies nothing that fresh measurements refute.** Never "the plan says this is
93
98
  acceptable" as a reason — answer anew: *What is the best thing, given what I know NOW?* If it
94
99
  differs: say so out loud, update the plan.
@@ -143,20 +148,40 @@ The board in the app shows only what you report: if you don't, it shows "Open" f
143
148
  If it creates a project, you pass on the **one** sentence it prints ("I created the project '…' in the app.").
144
149
  If two projects have the same name, or it was deleted in the app, it asks: ask the person and never choose yourself; `--new`
145
150
  only after their yes. If the success profile is missing, say the sentence once, keep working and report nothing.
146
- - **You report at six moments**, each time with `kimal3 plan report` (input: one report as JSON or a list,
151
+ - **You report at seven moments**, each time with `kimal3 plan report` (input: one report as JSON or a list,
147
152
  e.g. `echo '[…]' | kimal3 plan report`; the program sets time and session). You read the keys of spec and story from the app
148
153
  with `kimal3 plan` — don't invent them.
149
- 1. **A spec is created or its stories change:**
150
- `{"art":"spec","schluessel":"2026-10-24-test-month","titel":"Test month","datei":"docs/superpowers/specs/2026-10-24-test-month-design.md","stories":[{"schluessel":"US-1","titel":"The test month starts"}]}`
151
- 2. **The build of a spec begins:** the stories being built now go to "in progress" — **before** you take the first build step or
154
+ 1. **A spec comes into being or its stories change:** you report a new spec **as soon as the person says a spec should be
155
+ written** (or agrees to your suggestion of one) — before the first question back, before the first written sentence, even
156
+ without stories. The key is the file name it will get, without `.md`. When you hand it to the person to read (after your own
157
+ review rounds), you report it with its stories and `"wartet_auf_lesen":true` — the card then shows "Waiting for you to
158
+ read". If they say it works, you report it with `"wartet_auf_lesen":false`; if they say what doesn't work, the label stays
159
+ until you have revised it and they say it works. If you revise it after "works" so that they have to read it again, you set
160
+ it again. 🔑 **A spec is one card:** no side cards like "Write spec: …" or "Build plan: …", neither as a spec nor as a topic.
161
+ `{"art":"spec","schluessel":"2026-10-24-test-month-design","titel":"Test month","datei":"docs/superpowers/specs/2026-10-24-test-month-design.md","stories":[]}`
162
+ `{"art":"spec","schluessel":"2026-10-24-test-month-design","titel":"Test month","datei":"docs/superpowers/specs/2026-10-24-test-month-design.md","stories":[{"schluessel":"US-1","titel":"The test month starts"}],"wartet_auf_lesen":true}`
163
+ 2. **The topic in the chat is a spec** (the person talks about one, or you are creating one): whenever the topic switches to
164
+ another spec, not with every message; when in doubt, report — sending twice does no harm. The card then shows "In
165
+ discussion". For a new spec, both in one list, the spec first. If the person says in the chat that they are done with it,
166
+ you report the end with `"spec":null` and always name the spec you were discussing in `"war"` — if the person has clicked
167
+ another card in the meantime, your report then doesn't end that card's discussion. Always with the session, so without
168
+ `--no-session`. If the app says "Another chat is discussing this card right now.": do nothing, another chat carries the
169
+ discussion. If it says "… needs the chat it comes from.": report again with the session, not with `--no-session`. If it
170
+ says "This chat has the old board mod.": tell the person to type `/reload-plugins` or restart Claude, then report again.
171
+ If it says "This chat is no longer open" (a stored report arrived later): do nothing — if the topic still applies,
172
+ report it from the chat you are talking in now.
173
+ `{"art":"gespraech","spec":"2026-10-24-test-month-design"}` · `{"art":"gespraech","spec":null,"war":"2026-10-24-test-month-design"}`
174
+ 3. **The build of a spec begins:** the stories being built now go to "in progress" — **before** you take the first build step or
152
175
  send off a subagent:
153
- `{"art":"story","spec":"2026-10-24-test-month","story":"US-1","stand":"in_arbeit"}`
154
- 3. **A story is built and its counter-checks have run:** "built" with criteria and the `testen` sentence. The sentence is a guide for someone without technical knowledge: where to find it, what to do, what must appear, how to notice it is wrong. A command only if there is no other way - then say where to type it (in Claude Code in the project folder, with `!` in front) and put it in backticks. Without a command: "In the app open 'Metrics' and click the post from 14 Oct - it says '4,210 seen'. If a cell is empty, say 'Doesn't work'." With a command: "In Claude Code in the project folder type `! node wortzaehler.js beispiel.txt` - five lines appear, at the top 'der (4)'. If an error message appears, say 'Doesn't work'."
176
+ `{"art":"story","spec":"2026-10-24-test-month-design","story":"US-1","stand":"in_arbeit"}`
177
+ 4. **A story is built and its counter-checks have run:** "built" with criteria and the `testen` text. You take the text from the story's box "How you test it", word for word. It is a guide for someone without technical knowledge: **one line per step** (where to find it, what to do, what must appear), **without** the box heading, and **last** the line "Doesn't work if: …". In the JSON you separate the lines with `\n` — a real line break inside the text breaks the JSON, and `kimal3 plan report` cannot read the report. At most 1000 characters: if it is longer, shorten the steps, never cut off in the middle of a sentence. A command only if there is no other way - then say where to type it (in Claude Code in the project folder, with `!` in front) and put it in backticks.
155
178
  Example:
156
- `{"art":"story","spec":"2026-10-24-test-month","story":"US-1","stand":"gebaut","kriterien":[{"text":"If Sabine starts on 1 Nov, it ends on 30 Nov.","gegenprobe":"bestanden"}],"testen":"In the app open 'Test month' and click Start - below it says 'Ends on 30 Nov'. If it shows another date, say 'Doesn't work'."}`
157
- 4. **Something comes up that no spec promises:** `{"art":"thema","schluessel":"T-4","text":"The calendar could show public holidays"}`
158
- 5. **`/k3plan`:** check the specs against the code and report every deviation individually — it says how.
159
- 6. **Wrap-up:** reconcile the day — it says how.
179
+ `{"art":"story","spec":"2026-10-24-test-month-design","story":"US-1","stand":"gebaut","kriterien":[{"text":"If Sabine starts on 1 Nov, it ends on 30 Nov.","gegenprobe":"bestanden"}],"testen":"1. In the app open 'Test month'.\n2. Click Start.\n3. Below it says 'Ends on 30 Nov'.\nDoesn't work if: it shows another date."}`
180
+ 5. **Something comes up that no spec promises:** `{"art":"thema","schluessel":"T-4","text":"The calendar could show public holidays"}`
181
+ 6. **`/k3plan`:** check the specs against the code and report every deviation individually — it says how. **Checking is work:** a story with pending counter-checks (column "Claude test pending") that you check against the code, you report as "in progress" beforehand, with `"pruefen":true` — so the card doesn't come into discussion meanwhile. Stories under "Your test" or "Done" you do not report again during the reconciliation.
182
+ 7. **Wrap-up:** reconcile the day — it says how.
183
+
184
+ 🔑 **If a story stays unfinished when you stop** (at the end of `/k3plan` or in the wrap-up), you report it with `--no-session` (`kimal3 plan report --no-session`): its plan state stays `in_arbeit`, but the dot at the project stops glowing although the window stays open — on the board it then sits under "Open" as started.
160
185
 
161
186
  You report "built" only after a counter-check that ran in this session, never from memory.
162
187
  - **Subagents never report.** The mod reminds only you, not them: you report "in progress" **before** the job to a subagent that
@@ -167,7 +192,8 @@ The board in the app shows only what you report: if you don't, it shows "Open" f
167
192
  and goes along with the next command, don't send it again. `2` means not signed in: tell them `kimal3 login`.
168
193
  - **Sentences only you get** (from the mod `kimal3-plan`; the person doesn't see them): the reminder to report a story as "in
169
194
  progress" or to note the change as a topic · "create the project with `kimal3 project connect`" · "saved reports are
170
- waiting — `kimal3 plan send`". Act on them without telling the person.
195
+ waiting — `kimal3 plan send`" · the person clicked a card on the board to discuss it, or ended the discussion (then you talk
196
+ about that spec, or no longer; you don't report a `gespraech` for it). Act on them without telling the person.
171
197
 
172
198
  ## 4 · Permission and safety
173
199
  - **Before an action has to be confirmed**, explain in everyday language: **what** happens (the effect, not the
@@ -40,6 +40,8 @@ export function meldungFehler(m) {
40
40
  case "spec":
41
41
  if (!istText(m.schluessel) || !istText(m.titel) || !istTextOderNull(m.datei) || !Array.isArray(m.stories))
42
42
  return "meldung";
43
+ if (m.wartet_auf_lesen !== undefined && typeof m.wartet_auf_lesen !== "boolean")
44
+ return "meldung";
43
45
  return m.stories.every((s) => istObjekt(s) && istText(s.schluessel) && istText(s.titel)) ? null : "meldung";
44
46
  case "story":
45
47
  if (!istText(m.spec) || !istText(m.story) || typeof m.stand !== "string" || !STAENDE.includes(m.stand))
@@ -50,10 +52,13 @@ export function meldungFehler(m) {
50
52
  return "meldung";
51
53
  if (m.befunde !== undefined && !Array.isArray(m.befunde))
52
54
  return "meldung";
55
+ if (m.pruefen !== undefined && typeof m.pruefen !== "boolean")
56
+ return "meldung";
53
57
  return (m.testen === undefined || istTextOderNull(m.testen)) && (m.grund === undefined || istTextOderNull(m.grund)) ? null : "meldung";
54
58
  case "thema": return istText(m.schluessel) && istText(m.text) ? null : "meldung";
55
59
  case "uebernommen": return Number.isInteger(m.rueckmeldung) && istText(m.antwort) ? null : "meldung";
56
60
  case "eingeordnet": return istText(m.schluessel) && istText(m.text) && istText(m.antwort) ? null : "meldung";
61
+ case "gespraech": return istTextOderNull(m.spec) && (m.war === undefined || (istText(m.war) && m.spec === null)) ? null : "meldung";
57
62
  default: return "art";
58
63
  }
59
64
  }
@@ -29,7 +29,7 @@ const de = {
29
29
  Meldet der Projektseite eine Änderung: liest eine Meldung oder eine Liste
30
30
  von Meldungen als JSON von der Eingabe, zum Beispiel
31
31
  echo '{"art":"story","spec":"testmonat","story":"US-2","stand":"in_arbeit"}' | kimal3 plan melde
32
- Arten: spec, story, thema, uebernommen, eingeordnet.
32
+ Arten: spec, story, thema, uebernommen, eingeordnet, gespraech.
33
33
 
34
34
  --ohne-sitzung Meldet ohne die Nummer der Claude-Sitzung (für das
35
35
  Prüfen von Specs): Auf dem Board leuchtet kein Punkt.
@@ -91,7 +91,7 @@ const en = {
91
91
  Reports a change to the project page: reads one report or a list of
92
92
  reports as JSON from the input, for example
93
93
  echo '{"art":"story","spec":"testmonat","story":"US-2","stand":"in_arbeit"}' | kimal3 plan report
94
- Kinds (field "art"): spec, story, thema, uebernommen, eingeordnet.
94
+ Kinds (field "art"): spec, story, thema, uebernommen, eingeordnet, gespraech.
95
95
 
96
96
  --no-session Reports without the Claude session number (for checking
97
97
  specs): no dot lights up on the board.
@@ -1,7 +1,7 @@
1
1
  const de = {
2
2
  // ── skillInstall ──
3
3
  skillMissing: "Das Skill liegt nicht im Paket. Bitte kimal3 neu installieren:",
4
- skillWriteFailed: (fehler) => `Das Skill liess sich nicht schreiben: ${fehler}`,
4
+ skillWriteFailed: (fehler) => `Das Skill ließ sich nicht schreiben: ${fehler}`,
5
5
  skillUpdated: "✓ Skill aktualisiert.",
6
6
  skillCreated: "✓ Skill angelegt.",
7
7
  skillOnlyInstalled: " Das Skill ist installiert, die Slash-Befehle sind es NICHT.",
@@ -11,36 +11,36 @@ const de = {
11
11
  skipped2: " sie bleibt unangetastet. Wer die kimal3-Fassung will, benennt",
12
12
  skipped3: " die eigene um und führt den Befehl erneut aus.",
13
13
  unreadable: (anzahl, liste) => `⚠ ${anzahl} nicht lesbar: ${liste}`,
14
- unreadable1: " Diese Dateien liessen sich nicht öffnen — vielleicht sind sie",
14
+ unreadable1: " Diese Dateien ließen sich nicht öffnen — vielleicht sind sie",
15
15
  unreadable2: " gerade in Benutzung. Sie wurden nicht angefasst; ein zweiter",
16
16
  unreadable3: " Versuch gleich kann klappen.",
17
17
  noCommandInstalled1: " Es wurde KEIN Slash-Befehl installiert.",
18
18
  noCommandInstalled2: " Das Skill selbst ist installiert und funktioniert.",
19
19
  notAllWritten1: " Nicht alle Slash-Befehle konnten geschrieben werden.",
20
20
  notAllWritten2: " Die oben genannten stehen; ein zweiter Lauf holt den Rest.",
21
- runIncomplete: " Der Lauf ist damit unvollstaendig -- ein zweiter Versuch holt den Rest.",
22
- // ── die taegliche Pruefung (Wache) in Claudes Einstellungen ──
23
- watchSetUp: " Die taegliche kimal3-Pruefung ist eingetragen. Sie meldet sich nur, wenn etwas ansteht.",
24
- watchAlready: " Die taegliche kimal3-Pruefung steht schon in deinen Einstellungen.",
25
- watchFailed: " Die taegliche kimal3-Pruefung konnte NICHT eingetragen werden.",
21
+ runIncomplete: " Der Lauf ist damit unvollständig -- ein zweiter Versuch holt den Rest.",
22
+ // ── die tägliche Prüfung (Wache) in Claudes Einstellungen ──
23
+ watchSetUp: " Die tägliche kimal3-Prüfung ist eingetragen. Sie meldet sich nur, wenn etwas ansteht.",
24
+ watchAlready: " Die tägliche kimal3-Prüfung steht schon in deinen Einstellungen.",
25
+ watchFailed: " Die tägliche kimal3-Prüfung konnte NICHT eingetragen werden.",
26
26
  settingsUnreadable: (datei) => ` Deine Claude-Einstellungen sind nicht lesbar: ${datei}`,
27
- settingsNotJson: " Die Datei ist kein gueltiges JSON. Sie wurde NICHT angefasst.",
27
+ settingsNotJson: " Die Datei ist kein gültiges JSON. Sie wurde NICHT angefasst.",
28
28
  settingsStrangeShape: " Die Datei hat eine Form, die wir nicht verstehen. Sie wurde NICHT angefasst.",
29
29
  settingsRetryNoHelp: " Wiederholen hilft nicht -- erst die Datei in Ordnung bringen.",
30
30
  settingsFailedLine: (datei, ursache) => ` ${datei}: ${ursache}`,
31
- settingsUnchanged: " Deine bisherigen Einstellungen sind unveraendert.",
31
+ settingsUnchanged: " Deine bisherigen Einstellungen sind unverändert.",
32
32
  // Die Ursachen der vier Schritte aus einstellungen-schreiben.ts; `detail` ist die Meldung des Systems.
33
33
  stepRead: (detail) => `nicht lesbar (${detail})`,
34
- stepBackup: (detail) => `keine Sicherungskopie moeglich (${detail})`,
34
+ stepBackup: (detail) => `keine Sicherungskopie möglich (${detail})`,
35
35
  stepWrite: (detail) => `nicht schreibbar (${detail})`,
36
- stepCheck: (detail) => "Kontrolle nach dem Schreiben fehlgeschlagen (" + (detail ?? "unser Eintrag steht nicht in der zurueckgelesenen Datei") + ")",
36
+ stepCheck: (detail) => "Kontrolle nach dem Schreiben fehlgeschlagen (" + (detail ?? "unser Eintrag steht nicht in der zurückgelesenen Datei") + ")",
37
37
  // ── der Schluss ──
38
38
  tipK3: " Tipp /k3 in Claude Code. (Taucht nichts auf, einmal neu starten.)",
39
39
  tipOther: (name) => ` Tipp /${name} in Claude Code. (Taucht nichts auf, einmal neu starten.)`,
40
40
  // ── slashBefehleInstallieren ──
41
41
  commandsMissing: "Die Slash-Befehle liegen nicht im Paket. Bitte kimal3 neu installieren.",
42
42
  commandsNone: "Im Paket liegt kein einziger Slash-Befehl. Bitte kimal3 neu installieren.",
43
- commandsWriteFailed: (fehler) => `Die Slash-Befehle liessen sich nicht alle schreiben: ${fehler}`,
43
+ commandsWriteFailed: (fehler) => `Die Slash-Befehle ließen sich nicht alle schreiben: ${fehler}`,
44
44
  // ── raeumeVeralteteAuf ──
45
45
  outdatedRemoved: (name) => ` (Befehl /${name} entfernt: veraltet oder in einer anderen Sprache)`,
46
46
  };
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "kimal3",
3
- "version": "0.7.0",
3
+ "version": "0.9.0",
4
4
  "description": "Trag deine KI-Projekte dort ein, wo sie entstehen: im Terminal. · Log your AI projects where they happen: in the terminal.",
5
5
  "type": "module",
6
6
  "bin": {
@@ -21,22 +21,31 @@ und überspring ihn — kein Leerlauf.
21
21
  - **Das Board abgleichen — nur in einem Projektordner mit Projekt in der App** (sonst überspring
22
22
  es und sag nichts). `kimal3 plan` zeigt den Stand, den die App kennt; halt ihn gegen das, was
23
23
  heute wirklich passiert ist. Was fertig ist und dessen Gegenproben in dieser Sitzung gelaufen
24
- sind, steht als `gebaut` mit Kriterien und `testen`-Satz; was angefangen und nicht fertig ist,
25
- bleibt `in_arbeit`; was heute aufgefallen ist und keine Spec verspricht, kommt als `thema` hinein.
26
- Melde nur, was vom Stand abweicht, in einer Liste mit `kimal3 plan melde` (Aufbau und Rückgabewerte:
24
+ sind, steht als `gebaut` mit Kriterien und `testen`-Text; was angefangen und nicht fertig ist,
25
+ bleibt `in_arbeit` — und geht in einen **eigenen** Aufruf `kimal3 plan melde --ohne-sitzung`, getrennt von der Liste der fertigen (eine gemischte Liste ohne den Schalter bindet auch die unfertige Story an die Sitzung, und der Punkt leuchtet weiter, obwohl das Fenster nur offen steht); was heute aufgefallen ist und keine Spec verspricht, kommt als `thema` hinein.
26
+ Melde nur, was vom Stand abweicht: die fertigen in einer Liste mit `kimal3 plan melde` (Aufbau und Rückgabewerte:
27
27
  Coach, Abschnitt 3.6, und `/k3plan`, Abschnitt 6; was ein Rückgabewert heißt, steht in
28
28
  `~/.claude/skills/kimal3/SKILL.md`):
29
29
 
30
30
  ```json
31
- [ { "art": "story", "spec": "2026-10-24-testmonat", "story": "US-1", "stand": "gebaut",
31
+ [ { "art": "story", "spec": "2026-10-24-testmonat-design", "story": "US-1", "stand": "gebaut",
32
32
  "kriterien": [ { "text": "Startet Sabine am 1.11., endet er am 30.11.", "gegenprobe": "bestanden" } ],
33
- "testen": "Öffne /testmonat und klick „Starten“ — darunter steht „Endet am 30.11.“." },
34
- { "art": "story", "spec": "2026-10-24-testmonat", "story": "US-2", "stand": "in_arbeit" } ]
33
+ "testen": "1. Öffne /testmonat.\n2. Klick „Starten“.\n3. Darunter steht „Endet am 30.11.“.\nPasst nicht, wenn: dort ein anderes Datum steht." } ]
34
+ ```
35
+
36
+ Und was unfertig bleibt, getrennt davon, mit dem Schalter:
37
+
38
+ ```json
39
+ [ { "art": "story", "spec": "2026-10-24-testmonat-design", "story": "US-2", "stand": "in_arbeit" } ]
40
+ ```
41
+
42
+ ```
43
+ echo '[ … ]' | kimal3 plan melde --ohne-sitzung
35
44
  ```
36
45
 
37
46
  Bei Erfolg sagst du dazu nichts. Nennst du im Abschluss (Schritt 6) etwas zum Board, dann nur,
38
47
  was **nicht** geklappt hat (eine Absage, oder gemerkt, weil die App nicht erreichbar war).
39
- Der Punkt am Projekt auf der Projektseite bleibt, solange das Fenster offen ist; schließt der
48
+ Der Punkt am Projekt auf der Projektseite bleibt für laufende Arbeit, solange das Fenster offen ist; schließt der
40
49
  Mensch es, ist er in unter einer Sekunde weg.
41
50
 
42
51
  ## 2. Status-Datei nachziehen — und aufräumen
@@ -43,7 +43,7 @@ Du löschst sie nicht selbst.
43
43
  **Was die Ausgabe heißt** (Beispiel, erfundene Werte):
44
44
 
45
45
  ```
46
- Spec 2026-09-23-content-planer · Content-Planer als Seite (plan/2026-09-23-content-planer-seite-spec.md)
46
+ Spec 2026-09-23-content-planer · Content-Planer als Seite (plan/2026-09-23-content-planer.md)
47
47
  US-1 · gebaut · Runde 1 · Beiträge anlegen
48
48
  US-2 · in Arbeit · Runde 1 · Beiträge im Kalender verschieben
49
49
  Notiertes Thema T-3: Export als PDF
@@ -101,7 +101,7 @@ Reihenfolge.
101
101
  **Der Stand je Story (`stand`):**
102
102
  - `offen` — noch nichts gebaut.
103
103
  - `in_arbeit` — teilweise gebaut, oder ein Befund ist offen.
104
- - `gebaut` — gebaut. Das Datum setzt die App; dazu ein `testen`-Satz (Abschnitt 4).
104
+ - `gebaut` — gebaut. Das Datum setzt die App; dazu ein `testen`-Text (Abschnitt 4).
105
105
  - `weggelassen` — bewusst nicht gebaut, `grund` ist Pflicht (Regel 8). Nur, wenn die Spec oder
106
106
  der Mensch das so entschieden hat — nie von dir allein, um aufzuräumen. Im Zweifel: `offen`
107
107
  lassen und im Bericht fragen.
@@ -115,8 +115,9 @@ lesen.
115
115
  - `bestanden` — **nur**, wenn die Gegenprobe in dieser Sitzung gelaufen ist und das erwartete
116
116
  Ergebnis gezeigt hat. Nie aus dem Gedächtnis, nie vom letzten Mal, nie weil der Code „richtig
117
117
  aussieht".
118
- - `gescheitert` — sie ist gelaufen und hat etwas anderes gezeigt. Das ist ein Befund (Regel 1);
119
- die App stellt die Story und ihre Spec damit nach „In Arbeit".
118
+ - `gescheitert` — sie ist gelaufen und hat etwas anderes gezeigt. Das ist ein Befund (Regel 1):
119
+ Die Story trägt damit ⚠ und steht in „In Arbeit“, solange eine Sitzung daran arbeitet, sonst in
120
+ „Offen“ — ihre Spec kommt nicht nach „Dein Test“.
120
121
  - `offen` — alles, was nicht gelaufen ist: braucht einen Browser, eine Anmeldung, echte Daten
121
122
  oder einen Menschen. Lesen zählt nur, wenn das Kriterium etwas über die Datei selbst sagt (eine
122
123
  Datei gibt es, ein Text steht so da) — ein Verhalten beweist Lesen nicht.
@@ -127,7 +128,11 @@ mehr gebaut oder geprüft wird (die Spec steht dann in „Dein Test"). Bis dahin
127
128
  bestandenen Stories in der App „Von Claude geprüft". Sag im Bericht, was fehlt, damit die
128
129
  Gegenprobe laufen kann.
129
130
 
130
- **Der `testen`-Satz** (bei jeder `gebaut`-Story, höchstens 1000 Zeichen) ist eine Anleitung für jemanden ohne Technik. Er sagt wo man es findet, was man tut, was dann zu sehen ist, woran man merkt, dass es nicht stimmt. Ein Befehl nur, wenn es keinen anderen Weg gibt — dann sagst du, wo man ihn eingibt (in Claude Code im Projektordner, mit `!` davor), und setzt ihn in Backticks. Ohne Befehl: „Öffne in der App ‚Kennzahlen‘ und klick auf den Beitrag vom 14.10. — dort steht ‚4.210 gesehen‘. Steht dort eine leere Zelle, sag ‚Passt nicht‘.“ Mit Befehl: „Tippe in Claude Code im Projektordner `! node wortzaehler.js beispiel.txt` — es erscheinen fünf Zeilen, oben ‚der (4)‘. Kommt eine Fehlermeldung, sag ‚Passt nicht‘.“ Fehlt der Satz, zeigt die App: „Claude hat nicht aufgeschrieben, wie man das testet".
131
+ **Der `testen`-Text** (bei jeder `gebaut`-Story, höchstens 1000 Zeichen) ist eine Anleitung für jemanden ohne Technik. Steht die Story in einer Spec mit der Kiste „So testest du es“, nimmst du ihn von dort, wörtlich; fehlt die Kiste, schreibst du ihn selbst. **Eine Zeile je Schritt** — wo man es findet, was man tut, was dann zu sehen ist —, **ohne** Kistenüberschrift, und **zuletzt** die Zeile „Passt nicht, wenn: …“. Im JSON trennst du die Zeilen mit `\n`: Ein echter Zeilenumbruch im Text bricht das JSON, und `kimal3 plan melde` liest die Meldung nicht. Ist der Text länger als 1000 Zeichen, kürze die Schritte — nie mitten im Satz abschneiden, die Zeile „Passt nicht, wenn: …“ muss am Ende stehen bleiben. Ein Befehl nur, wenn es keinen anderen Weg gibt — dann sagst du, wo man ihn eingibt (in Claude Code im Projektordner, mit `!` davor), und setzt ihn in Backticks. Fehlt der Text, zeigt die App: „Claude hat nicht aufgeschrieben, wie man das testet".
132
+
133
+ **Prüfen ist Arbeit.** Bevor du eine Story mit offenen Gegenproben (Spalte „Claude-Test offen“) gegen den Code prüfst, meldest du sie als `in_arbeit` **mit** der Sitzung (also ohne `--ohne-sitzung`) **und mit `"pruefen": true`**: Solange du prüfst, leuchtet der Punkt am Projekt, aber die Karte kommt dadurch nicht ins Gespräch — ohne das Feld wanderte der blaue Rahmen durch jede Spec, die du prüfst. Nach der Prüfung meldest du das Ergebnis (`gebaut`, oder `in_arbeit` mit Befund — jede `in_arbeit`-Meldung aus `/k3plan` trägt `"pruefen": true`). Stories in „Dein Test“ oder „Fertig“ meldest du beim Abgleich **nicht** neu, auch wenn du sie durchsiehst: `in_arbeit` und danach `gebaut` setzt ihr Baudatum auf heute, und jede Meldung zeigt das Etikett „geändert“ und bei zwei Sitzungen das ⚠ „gleichzeitig geändert“. Was am Ende von `/k3plan` unfertig bleibt, meldest du mit `--ohne-sitzung` (Abschnitt 6).
134
+
135
+ **Wie eine Spec aufgebaut ist.** Findest du beim Prüfen eine Spec, die nicht so gebaut ist, sag es im Bericht — du schreibst sie nicht um. Eine Story steht darin in vier Kisten: **User Story** (der Titel nennt das Ziel des Menschen) · **Akzeptanzkriterium** (mit Gegenprobe) · **So testest du es** (nummerierte Schritte, darunter „Passt nicht, wenn: …“) · **Technische Notiz**.
131
136
 
132
137
  **Befunde** (`befunde`): nur **offene**. `quelle: "claude"` für etwas, das die Story verspricht und
133
138
  nicht tut, und das kein Kriterium abdeckt. `seit`: das Datum, an dem der Befund entstand. Ein
@@ -138,7 +143,7 @@ Befunde mit, nicht nur den neuen. Fehlt das Feld, bleibt die Liste, wie sie ist.
138
143
  - Sie beginnt bei `1` und wird **nie** kleiner; fehlt `runde` in der Meldung, bleibt sie.
139
144
  - **Um genau 1 erhöhen**, wenn eine Story mit einem Befund des Menschen (`quelle: "mensch"`)
140
145
  seitdem nachgebessert wurde (Git-Verlauf, und die Gegenproben bestehen jetzt): dann
141
- `befunde: []`, `stand: "gebaut"`, `runde` + 1, neuer `testen`-Satz. Der Mensch testet neu.
146
+ `befunde: []`, `stand: "gebaut"`, `runde` + 1, neuer `testen`-Text. Der Mensch testet neu.
142
147
  Ist unklar, ob nachgebessert wurde: Befund stehen lassen und im Bericht fragen.
143
148
  - **Auch erhöhen**, wenn du eine **bestätigte** Story so geändert hast, dass der Mensch es merken
144
149
  würde — sein altes „Passt" gilt dann nicht mehr (Regel 7).
@@ -148,11 +153,11 @@ Befunde mit, nicht nur den neuen. Fehlt das Feld, bleibt die Liste, wie sie ist.
148
153
 
149
154
  Die App zeigt sie dem Menschen in genau diesem Wortlaut („So bleibt die Planung kurz"):
150
155
 
151
- 1. **Ein Problem wird keine neue Karte.** Hält eine Story nicht, was sie verspricht — Claudes Prüfung fällt durch oder du sagst „Passt nicht" —, hängt das Problem (Befund) an **dieser** Story, und ihre Spec geht zurück nach „In Arbeit“.
156
+ 1. **Ein Problem wird keine neue Karte.** Hält eine Story nicht, was sie verspricht — Claudes Prüfung fällt durch oder du sagst „Passt nicht" —, hängt das Problem (Befund) an **dieser** Story. Sie steht in „Offen“, bis jemand daran arbeitet.
152
157
  2. **Neu ist nur, was niemand versprochen hat. Das kommt in den Eingang, und der hat fünf Plätze.**
153
- 3. **Claude sortiert jedes Thema beim nächsten Abgleich (`/k3plan`) ein:** als neue Story in eine Spec, als Befund an eine Story, oder gestrichen mit Begründung. „Für später" gibt es nicht. Was daraus wurde, steht unter „Von Claude einsortiert".
158
+ 3. **Claude sortiert jedes Thema beim nächsten Abgleich (`/k3plan`) ein:** als neue Story in eine Spec, als Befund an eine Story, oder gestrichen mit Begründung. „Für später" gibt es nicht.
154
159
  4. **Nichts liegt länger als 14 Tage im Eingang.**
155
- 5. **Höchstens eine Spec gleichzeitig in Arbeit** („In Arbeit“ und „Claude-Test offen“ zusammen). Erst fertig machen, dann die nächste beginnen.
160
+ 5. **Höchstens eine Spec gleichzeitig in Arbeit** („In Arbeit“ und „Claude-Test offen“ zusammen). „In Arbeit“ heißt: Eine Claude-Sitzung arbeitet gerade daran. Erst fertig machen, dann die nächste beginnen.
156
161
  6. **Höchstens fünf Stories warten auf deinen Test.** Sind es mehr, fängt Claude nichts Neues an, bis du getestet hast.
157
162
  7. **Fertig heißt zweimal geprüft:** Claude hat alles selbst ausprobiert, und du hast „Passt" gesagt — für genau diesen Stand.
158
163
  8. **Eine Spec ist erst abgeschlossen, wenn jede Story fertig oder bewusst weggelassen ist** — mit Grund. Einen stillen Rest gibt es nicht.
@@ -160,7 +165,7 @@ Die App zeigt sie dem Menschen in genau diesem Wortlaut („So bleibt die Planun
160
165
  **Was du danach tust** (jedes Mal eine Meldung, Abschnitt 6):
161
166
 
162
167
  - **Regel 1 — jedes `passt nicht` aus `kimal3 plan`:** Gibt es die Story noch, melde sie mit dem Satz
163
- des Menschen als Befund (`quelle: "mensch"`, `seit: "<heute>"`) und `stand: "in_arbeit"`, und
168
+ des Menschen als Befund (`quelle: "mensch"`, `seit: "<heute>"`), `stand: "in_arbeit"` und `"pruefen": true`, und
164
169
  gleich dahinter in derselben Liste `uebernommen` mit der Nummer: `{ "art": "uebernommen",
165
170
  "rueckmeldung": 12, "antwort": "Befund an US-2" }`. Ist sie seitdem schon nachgebessert,
166
171
  stattdessen `runde` + 1, `befunde: []` und `stand: "gebaut"` (Abschnitt 4). Gibt es die Story
@@ -181,10 +186,9 @@ Die App zeigt sie dem Menschen in genau diesem Wortlaut („So bleibt die Planun
181
186
  `gestrichen: Feiertage stehen schon im Kalender-Werkzeug.`
182
187
 
183
188
  Für eine Notiz aus der App (`#13 · Thema`) gehört die Antwort als **ein Satz** in eine Meldung
184
- `uebernommen` (die App zeigt sie unter „Zuletzt eingeordnet" als `<Notiz> → <Antwort>`); schreib
185
- sie darum **ohne** Pfeil am Anfang. Ein `Notiertes Thema` von dir ordnest du mit einer Meldung
186
- `eingeordnet` ein (Schlüssel, Text wie oben, Antwort) — die App nimmt es aus den Themen heraus
187
- und zeigt es 14 Tage lang unter „Zuletzt eingeordnet". Nenn die Einordnung auch im Bericht.
189
+ `uebernommen`, **ohne** Pfeil am Anfang. Ein `Notiertes Thema` von dir ordnest du mit einer Meldung
190
+ `eingeordnet` ein (Schlüssel, Text wie oben, Antwort) — die App nimmt es aus den Themen heraus.
191
+ Die Seite zeigt die Antwort nicht; nenn die Einordnung deshalb im Bericht.
188
192
  - **Regel 4:** Weil du bei jedem `/k3plan` alles einordnest, liegt nichts lange. Ein Thema, das
189
193
  schon mehr als 14 Tage liegt, ordnest du **auf jeden Fall** jetzt ein.
190
194
  - **Regel 5 und 6 — keine neue Spec beginnen**, solange eine andere Spec in Arbeit ist (eine ihrer
@@ -202,45 +206,59 @@ Die App zeigt sie dem Menschen in genau diesem Wortlaut („So bleibt die Planun
202
206
  ## 6. Die Meldungen
203
207
 
204
208
  Jede Meldung ist ein JSON-Objekt, mehrere eine Liste. Sie geht über die Eingabe an
205
- `kimal3 plan melde --ohne-sitzung`; das Programm setzt die Zeit selbst, das Projekt kommt vom Ordnerzettel
206
- `plan/projekt.json`. Prüfen ist nicht Arbeiten — so leuchtet auf dem Board kein Punkt.
209
+ `kimal3 plan melde`; das Programm setzt die Zeit selbst, das Projekt kommt vom Ordnerzettel
210
+ `plan/projekt.json`. Prüfen ist Arbeit — mit der Sitzung gemeldet leuchtet auf dem Board der Punkt, solange du prüfst; `"pruefen": true` an jeder `in_arbeit`-Meldung hält die Karte dabei aus dem Gespräch.
207
211
 
208
212
  ```
209
- echo '[ … ]' | kimal3 plan melde --ohne-sitzung
213
+ echo '[ … ]' | kimal3 plan melde
210
214
  ```
211
215
 
212
- (In PowerShell: `'[ … ]' | kimal3 plan melde --ohne-sitzung`. Lange Texte lieber über eine Datei.) Die Beispiele
216
+ (In PowerShell: `'[ … ]' | kimal3 plan melde`. Lange Texte lieber über eine Datei.) Die Beispiele
213
217
  sind erfunden.
214
218
 
219
+ **Ganz am Ende** meldest du die Stories, die unfertig bleiben (in Arbeit, Befund offen), noch einmal —
220
+ in einem **eigenen** Aufruf mit `--ohne-sitzung`, getrennt von der Liste der fertigen: Eine gemischte
221
+ Liste ohne den Schalter bindet auch die unfertige Story an die Sitzung, und der Punkt leuchtet weiter.
222
+ Mit dem Schalter bleibt der Plan-Stand `in_arbeit`, aber der Punkt leuchtet nicht weiter, während das
223
+ Fenster offen bleibt — auf dem Board steht die Story dann in „Offen“ als angefangen.
224
+
225
+ ```
226
+ echo '[ … ]' | kimal3 plan melde --ohne-sitzung
227
+ ```
228
+
215
229
  **Eine Spec** — beim Prüfen und wenn Stories dazukommen:
216
230
 
217
231
  ```json
218
- { "art": "spec", "schluessel": "2026-10-24-testmonat", "titel": "Testmonat",
232
+ { "art": "spec", "schluessel": "2026-10-24-testmonat-design", "titel": "Testmonat",
219
233
  "datei": "docs/superpowers/specs/2026-10-24-testmonat-design.md",
220
234
  "stories": [ { "schluessel": "US-1", "titel": "Der Testmonat startet" },
221
235
  { "schluessel": "US-2", "titel": "Der Testmonat endet" },
222
236
  { "schluessel": "US-3", "titel": "Export des Testmonats" } ] }
223
237
  ```
224
238
 
239
+ Lass dabei `wartet_auf_lesen` weg: Fehlt das Feld, bleibt das Etikett „Wartet auf dein Lesen“, wie es ist. Gesetzt und
240
+ weggenommen wird es, wenn du eine Spec dem Menschen zum Lesen vorlegst und er sie freigibt (Coach, Abschnitt 3.6) — genauso die Meldung
241
+ `gespraech`; `/k3plan` schickt keine.
242
+
225
243
  **Eine Story** — eine Abweichung, ein Eintrag. Gebaut, mit Gegenprobe:
226
244
 
227
245
  ```json
228
- { "art": "story", "spec": "2026-10-24-testmonat", "story": "US-1", "stand": "gebaut",
246
+ { "art": "story", "spec": "2026-10-24-testmonat-design", "story": "US-1", "stand": "gebaut",
229
247
  "kriterien": [ { "text": "Startet Sabine am 1.11., endet der Testmonat am 30.11.", "gegenprobe": "bestanden" } ],
230
- "testen": "Öffne in der App ‚Testmonat‘ und klick „Starten“ — darunter steht ‚Endet am 30.11.‘. Steht dort ein anderes Datum, sag ‚Passt nicht‘." }
248
+ "testen": "1. Öffne in der App ‚Testmonat‘.\n2. Klick „Starten“.\n3. Darunter steht ‚Endet am 30.11.‘.\nPasst nicht, wenn: dort ein anderes Datum steht." }
231
249
  ```
232
250
 
233
251
  Mit einem offenen Befund (hier von dir; `quelle: "mensch"` nur für den Satz des Menschen):
234
252
 
235
253
  ```json
236
- { "art": "story", "spec": "2026-10-24-testmonat", "story": "US-2", "stand": "in_arbeit",
254
+ { "art": "story", "spec": "2026-10-24-testmonat-design", "story": "US-2", "stand": "in_arbeit", "pruefen": true,
237
255
  "befunde": [ { "text": "Am 30.11. fehlt die Erinnerungsmail, die die Spec verspricht.", "quelle": "claude", "seit": "2026-10-23" } ] }
238
256
  ```
239
257
 
240
258
  Bewusst weggelassen (`grund` ist Pflicht):
241
259
 
242
260
  ```json
243
- { "art": "story", "spec": "2026-10-24-testmonat", "story": "US-3", "stand": "weggelassen", "grund": "Die Spec streicht den Export." }
261
+ { "art": "story", "spec": "2026-10-24-testmonat-design", "story": "US-3", "stand": "weggelassen", "grund": "Die Spec streicht den Export." }
244
262
  ```
245
263
 
246
264
  **Ein Thema** (Regel 2), **ein Thema von dir einordnen** (Regel 3), **eine Rückmeldung des Menschen
@@ -270,6 +288,8 @@ angemeldet: Sag dem Menschen `kimal3 login`; die Meldung ist gemerkt.
270
288
  | `Rückmeldung 12 gibt es in diesem Projekt nicht oder steht zweimal …` | Nur Nummern aus `kimal3 plan`, jede einmal. |
271
289
  | `Rückmeldung 12 („…“) ist als übernommen gemeldet, aber US-2 hat keinen Befund von dir …` | Erst die Story mit dem Befund `quelle: "mensch"` melden (Regel 1) — oder `runde` + 1, wenn nachgebessert ist — dann `uebernommen`. |
272
290
  | `Der Plan ist nicht lesbar: <Ort> …` | Die genannte Stelle der Meldung berichtigen (Länge, `grund` bei `weggelassen`, doppelter Schlüssel). |
291
+ | `Die Meldung „Im Gespräch“ braucht den Chat, aus dem sie kommt.` | Mit Sitzung noch einmal melden, nicht mit `--ohne-sitzung`. |
292
+ | `Über diese Karte spricht gerade ein anderer Chat.` | Nichts tun: Das Gespräch trägt ein anderer Chat. |
273
293
  | `Die Meldung ist angekommen, der Text von <Datei> aber nicht …` | Die Meldung noch einmal schicken — doppelt schadet nicht. Passt der Text nicht mehr (über 300 KB), sag es dem Menschen. |
274
294
  | `Die Meldungen sind gespeichert, aber noch nicht ganz vermerkt.` | Noch einmal schicken — doppelt schadet nicht. |
275
295
  | `Die gespeicherte Planung in der App ist beschädigt …` | Sag es dem Menschen. `kimal3 plan hoch --ueberschreiben` ersetzt die Planung durch eine ganze Datei `plan/stand.json` — **nur nach seinem ausdrücklichen Ja.** |
@@ -282,7 +302,7 @@ nicht, wenn die Meldung es vorschlägt.
282
302
  **Höchstens fünf Zeilen**, ohne Fachjargon — und nichts über die Meldungen selbst:
283
303
 
284
304
  - was **fertig** wurde (seit dem letzten Mal bestätigt),
285
- - was **auf seinen Test wartet** (nur Stories aus Specs in „Dein Test") — mit dem `testen`-Satz, damit er gleich loslegen kann,
305
+ - was **auf seinen Test wartet** (nur Stories aus Specs in „Dein Test") — mit dem `testen`-Text, damit er gleich loslegen kann,
286
306
  - was im **Eingang** entschieden wurde (jedes Thema mit seiner Antwort),
287
307
  - eine **Warnung**, wenn Regel 5 oder 6 verletzt ist: „Teste zuerst …" statt einer neuen Story,
288
308
  - der **Link** aus `Ansehen: …`.