19 KiB
title, type, created, status, baseline_commit, review_loop_iteration, context
| title | type | created | status | baseline_commit | review_loop_iteration | context | |
|---|---|---|---|---|---|---|---|
| Story 3.12 — Lease-Lifecycle und Commit-Abschluss transaktional schließen | feature | 2026-08-21 | in-progress | 80480af3ec |
0 |
|
Intent
Problem: Die Koordinations-Dimension ist über §5.11 (Leasing/Dirty-Tree, Story 3.5), §5.12 (Staleness/Recovery, Story 3.6), §5.13 (Phasen-Trennung, Story 3.7) und §5.17 (atomare Root-Scope-Lease-Akquise, Story 3.11) verankert — aber die Lifecycle-Klammer fehlt: Akquise, Dirty-Tree-Schutz, Mutation, Rollback und Freigabe sind nirgends als konsistenter, transaktionaler Lebenszyklus instruiert, der SUCCESS und FAIL jeweils einen sauberen, wiederanlaufbaren Zustand hinterlässt. Konkret unverankert: (a) Liveness einer lebenden Lease (eine höhere Generation macht sie nicht stale; Staleness verlangt bestätigten Abbruch oder abgelaufene Liveness plus atomare Ownership-Prüfung — epic-3-context Z. 43 „Zielzustand Review-Loop-3, P-11" und SCP 2026-08-20 Z. 71 „Staleness/Liveness"); (b) durable Release — nach Release sind Mutation, zulässiger Nachweis und Freigabe dauerhaft, Lock entfernt, Worktree sauber, Folge-Run besteht den Clean-Input-Guard; (c) Baseline-Rollback (Index + Worktree) aus dem bezeichneten Baseline-Commit mit leerem Post-Rollback-Diff (§5.3/§6-Pkt.-3-Mechanik nennt nur Bundle-/git checkout-Wiederherstellung, kein Index); (d) eine eindeutige Abort-/Protect-Zustandsmaschine für getrackte und ungetrackte fremde Änderungen (sandbox-3-5 L4 ist nur Inline-Ablauf, keine Zustandsmaschine); (e) stale-Übernahme genau einmal mit ersetzter Holder-ID und genau einer aktiven Root-Lease; (f) Kill-Point-Tests (termini undefiniert, nirgends verankert); (g) die Grenze des kanonischen Knowledge Logs (wiki/log.md nur vertragskonforme fachliche Änderungen + notwendige Koordinationsereignisse).
Approach: Neue Sektion §5.18 „Lease-Lifecycle & transaktionaler Commit-Abschluss (Story 3.12)" (nach §5.17, vor §6; Revision 3.7): additiv über §5.11/§5.12/§5.13/§5.17, Fugen-Identität — kein Umbau bestehender Wortlaute. Sie instruiert den geschlossenen Ablauf (1) Liveness-Ownership (nur bestätigter Abbruch/abgelaufene Liveness + atomare Ownership-Prüfung macht eine Lease stale; eine höhere Generation allein nicht), (2) stale-Übernahme genau einmal (genau eine aktive Root-Lease, ersetzte Holder-ID im log.md), (3) Abort-/Protect-Zustandsmaschine für fremde getrackte/ungetrackte Änderungen (Scratch-Zone scratch/<run-id>/ bzw. git stash push; byte-identischer Restore) samt UNCOMMITTED_INPUT-Abbruch abgestimmt mit §5.11 Pkt. 3, (4) Baseline-Rollback (Index + Worktree aus <Baseline-Commit>; Post-Rollback-Diff leer; Kill-Punkt nach Mutation/Staging), (5) durable Release (Mutation + zulässiger Log-/Koordinationsnachweis committet, Lock per Ref-Delete entfernt, Worktree sauber, unmittelbar folgender Run besteht den Clean-Input-Guard — sauberer Worktree ohne fremde/geschützte Reste), (6) kanonisches Log (§5/Koordination nur), (7) Kill-Point-Tests (vor Mutation, nach Mutation, vor Commit, nach Commit — je konsistenter Endzustand, §5.13-Pkt.-3-Zustands-Restaurations-Invariante).
Boundaries & Constraints
Always:
- Nur
schema/compiler.mdmutiert (neue §5.18 + §7-Bullet-Erweiterung Story-3.12 + §8-Revisionslog Revision 3.7).schema/validator.md,schema/wiki-compiler.md,adapters/,raw/read-only (AD-3);schema/canonical-terms.mdappend-only unangetastet.sprint-status.yaml,wiki/log.md,epic-3-context.md,deferred-work.mdwerden nur append/Sync-gepflegt. - Referenz statt Re-Negotiation: §5.11 (Pkt. 1–7), §5.12 (Pkt. 1–7), §5.13 und §5.17 bleiben textuell unverändert — §5.18 instruiert die Lifecycle-Ebene darüber und referenziert sie Wortlaut-unverändert. Fugen-Identität: Branch-Form
lease/<area>/<id>, Lockfile-Feld-Satz, Root-Scope-Umfang §5.11 Pkt. 2, atomarer scope-bezogener Lock §5.17. - Kein neues Prädikat, keine neue §7-Invaliditätsklasse, kein neuer Frontmatter-/Format-Key, kein Standalone (D-3), keine Wanduhr-/Systemzeit-Steuerung (A0-20: keine TTL über Kalenderzeit; Lifecycle deterministisch aus dem committeten Git-State, AD-17h/A0-19). Das
generated.at-Wanduhr-Gap (§5.14 Pkt. 3) bleibt unverändert. - Sandbox-Nachweis re-executierbar (Muster sandbox-3-11, Exit 0, harte PASS/FAIL,
/tmp-Baum, nie der reale Ist-Baum; kein Zugriff auf reales Bundle/raw/).
Ask First:
- Verhalten des
generated.at(A0-20) oder eine TTL-/Wanduhr-Steuerung ändern (bleibt benannter Defer bzw. bindend unverändert). - Änderung an §5.17-Pkt.-2-Ask-First-Klausel (atomares create-only-Primitiv nicht zuverlässig → HALT, Alternativ-Primitiv).
- Änderung an §5.11-Pkt.-1-/Pkt.-2-Wortlaut oder §5.12-Ankern (frozen, Fugen-Identität).
- Erweiterung des
schema/validator.mdum Lease-/Koordinations-Prüfpunkte (wäre Epic-1-Vertragsänderung — nicht Teil dieser Story).
Never:
- Kein Umschreiben bestehender §5.11/§5.12/§5.13/§5.17-Wortlaute; keine Wanduhr-TTL; keine stille Löschung fremder uncommitteter/geschützter Änderungen (AD-17e); keine Wissensmutation bei Orphan/Hold (AD-16-Default); kein textueller Auto-Merge (AD-17c); keine neue eigene LLM-Runtime/Workflow-Engine (AD-11, D-3); kein Standalone; keine Validator-Erweiterung ohne Autorisierung.
I/O & Edge-Case Matrix
| Scenario | Input / State | Expected Output / Behavior | Error Handling |
|---|---|---|---|
| LIVENESS_AKTIV | lebende Lease mit höherer Generation sichtbar | Lease bleibt aktiv; keine Stale-werdung allein durch Generationshöhe (AC-1) | kein Release, keine Fremd-Übernahme |
| STALE_UEBERNAHME | nachweislich stale Lease (bestätigter Abbruch / abgelaufene Liveness) | Übernahme gelingt genau einmal; ersetzte Holder-ID benannt; genau eine aktive Root-Lease (AC-2) | Ownership-Prüfung vor Übernahme; kein Doppel-Übernehmer |
| DIRTY_GETRACKT | fremde getrackte Änderung im Mutationsbereich | Abort-/Protect-Zustandsmaschine: schützen (Scratch/Stash), Restore byte-identisch nach Run (AC-3) | UNCOMMITTED_INPUT-Abbruch abgestimmt §5.11 Pkt. 3; nie gelöscht |
| DIRTY_UNGETRACKT | fremde ungetrackte Datei im Mutationsbereich | Protect: sichern + Restore; keine stillen Löschungen (AC-3) | nie gelöscht; log.md-Eintrag |
| ROLLBACK_NACH_MUTATION | Fehler nach Mutation/Staging | Rollback aus <Baseline-Commit>: Index + Worktree restauriert; Post-Rollback-Diff leer (AC-4) |
Kill-Punkt nach Mutation: konsistenter Endzustand |
| ROLLBACK_NACH_COMMIT_VOR_RELEASE | Fehler nach Commit, vor Release | Kill-Punkt vor Commit/vor Release: Zustand == Baseline oder valide committet; kein Teilzustand veröffentlicht (AC-4) | Commit-Boundary = Mutation-Boundary (AD-17f) |
| RELEASE_DURABLE | erfolgreicher Run | Mutation + zulässiger Log-/Koordinationsnachweis committet; Lock per Ref-Delete entfernt; Worktree sauber; Folge-Run besteht Clean-Input-Guard (AC-5) | Release-Fehler = HARD-FAIL; Lock nie hängend |
| KANONISCHES_LOG | Run-Historie schreiben | wiki/log.md nur vertragskonforme fachliche Änderungen + notwendige Koordinationsereignisse; Build-/Review-/Story-/Sandbox-Historie außerhalb (AC-6) |
Verstoß = textuell benannt (NFR-4) |
| KILLPUNKT_VOR_MUTATION | vor erster Mutation | Zustand == Baseline; keine Zwischenstände (AC-7) | konsistenter Endzustand, Determinismus |
| KILLPUNKT_NACH_MUTATION | nach Mutation | Zustand == valider Zwischenstand (geplanter Plan-Freeze); kein Ghost-Diff außerhalb erlaubter Menge (AC-7) | §5.9-Pkt.-5-Ghost-Diff-Rollback |
| KILLPUNKT_VOR_COMMIT | nach Staging, vor Commit | nur erlaubte Pfad-Menge staged; kein Teilzustand committet (AC-7) | Commit-Boundary = Mutation-Boundary |
| KILLPUNKT_NACH_COMMIT | nach Commit | Bundle == valide committeter Zustand; anschließbar an Clean-Input-Guard (AC-7) | kein hängender Lock, sauberer Worktree |
Code Map
schema/compiler.md— primär mutiert (D-3): neue Sektion §5.18 „Lease-Lifecycle & transaktionaler Commit-Abschluss (Story 3.12)" (nach §5.17 Z. 415–424, vor §6 Z. 426; Pkt. 1–7); §7-Bullet-Erweiterung (Story-3.12-Verankerung analog §5.17-/§5.15-Ergänzung bei Z. 471ff); §8-Revisionslog Revision 3.7 (Z. 486ff, nach Z. 527). Bestehende §5.11 (Z. 304–321)/§5.12 (Z. 323–342)/§5.13 (Z. 344–363)/§5.17 (Z. 415–424) bleiben textuell unverändert (Fugen-Identität; §5.17-Pkt.-1-Z. 419 „Lifecycle-Regie Story 3.12" und Pkt.-6-Z. 424 „bleibt Story 3.12" sind die Anschluss-Sutur)._bmad-output/implementation-artifacts/sandbox-3-12/run-sandbox.sh— neu (re-executierbar, Mustersandbox-3-11/run-sandbox.sh544 Z., Exit 0): Lifecycle-Szenarien L-1..L-9 (Matrix-Zeilen als harte Assertionen); übernimmt die 3-11-Bausteine (isolate()Z. 99–109,scopelock_acquire()Z. 124–131,scopelock_release()Z. 132–141 mit Ownership-Prüfung,scopelock_content()Z. 142–148,assert_frontmatter()Z. 164–173,runlabel/pass/failZ. 98/179–180) und ergänzt: Abort-/Protect-Zustandsmaschine (aus sandbox-3-5-L4-Inline Z. 379–434:db_checkZ. 223–234, Stash/Scratch Z. 416–421, Restore Z. 422–425), Registry/Gen/Liveness (aus sandbox-3-6:reg_genZ. 219–224,lease_staleZ. 277–283,reg_write/reg_bumpZ. 233–256,reg_stale_markZ. 257–264,free_leaseZ. 338–343), Baseline-Rollback Index+Worktree (via §5.13-Pkt.-3 Z. 359 „Post-Rollback-Diff gg. Baseline leer"), Kill-Point-Tests (4 Konsistenz-Assertions), Clean-Input-Guard (Worktree-Sauberkeitsprüfung nach Release). Kein Zugriff auf reales Bundle/raw/._bmad-output/implementation-artifacts/sandbox-3-11/run-sandbox.sh— read-only Vorbild (Ableitungs-Pflicht:scopelock_release-Ownership,isolate-Ref-Reset, A-8-Relase-erneut Z. 501–523; Defer „scopelock_header_banner" Z. 166/175 → Home 3.12)._bmad-output/implementation-artifacts/sandbox-3-5/run-sandbox.sh— read-only Quelle der Dirty-Tree-Mechanik (L4 Z. 379–434:db_checkZ. 223–234, UNCOMMITTED_INPUT-Abbruch Z. 395–415, Stash/Scratch Z. 416–421, Restore Z. 422–425, NIE-gelöscht Z. 426–428)._bmad-output/implementation-artifacts/sandbox-3-6/run-sandbox.sh— read-only Quelle der Registry/Stale-/Recovery-Mechanik (Registry Z. 216–245, Gen Z. 219–224/246–256,lease_staleZ. 277–283, Stale-Mark/Übernahme Z. 257–264/346–478,raw/-Recovery STALE-4 Z. 451–478,assert_no_wallclockZ. 294–300)._bmad-output/implementation-artifacts/sprint-status.yaml— mutiert: Key3-12-lease-lifecycle-und-commit-abschluss-transaktional-schliessenbacklog→review(Implementierungs-Commit; finalerdone-Flip im Step-05-Status-Sync nach konvergiertem Review-Loop);last_updated(FormatMM-DD-YYYY HH:MM).wiki/log.md— append (Vertrag §5): Story-3.12-Eintrag (Verankerung §5.18, Sandbox L-1..L-9, Status-Flip, Validator-Verdikt) — nur vertragskonforme fachliche + Koordinationsereignisse (AC-6)._bmad-output/implementation-artifacts/deferred-work.md— append: Story-3.12-relevante Defers aus Review-Loop-1-Story-3.11 als aufgegriffen markieren („Sandbox-3.5/-3.6-check-then-act-Abgleich", „Banner-/I-O-Matrix-Kosmetik", „scopelock_header_banner"-Platzhalter) bzw. benannte Home-Zuordnung._bmad-output/implementation-artifacts/epic-3-context.md— mutiert („Edit freely"): Technical Decision Z. 43 „Transaktionaler Lifecycle" von „Zielzustand… nicht verankert" auf Ist-Zustand (§5.18) aktualisieren.
Read-only evidence (AD-3): schema/validator.md (Rev 9 — prüft keine Lease-/Koordinationszustände, Z. 194/195 nur stale_after-Lebenszyklus-WARN; Validator-Erweiterung nicht Teil dieser Story), schema/wiki-compiler.md, adapters/, raw/ (z. B. raw/prd/…, raw/epics/…). schema/canonical-terms.md append-only unangetastet.
Tasks & Acceptance
Execution:
schema/compiler.md— §5.18 einfügen (nach §5.17, vor §6): Pkt. 1–7 gemäß Intent; §7-Bullet und §8-Revisionslog Revision 3.7 nachführen; bestehende §5.11/§5.12/§5.13/§5.17 textuell unverändert (Fugen-Identität)_bmad-output/implementation-artifacts/sandbox-3-12/run-sandbox.sh— L-1..L-9 (Lifecycle, Abort-/Protect-Zustandsmaschine, Baseline-Rollback Index+Worktree, Kill-Point-Tests, Clean-Input-Guard), harte PASS/FAIL, Exit 0,/tmp-Baum, nie realer Ist-Baum_bmad-output/implementation-artifacts/sprint-status.yaml— Key 3-12 →review(Impl-Commit; finalerdone-Flip Step-05);last_updatedaktualisierenwiki/log.md— Story-3.12-Eintrag (Verankerung, Sandbox, Status-Flip, Validator-Verdikt) — nur vertragskonforme Inhalte (AC-6)_bmad-output/implementation-artifacts/deferred-work.md— relevante Story-3.12-Home-Defers als aufgegriffen markieren/zuordnen_bmad-output/implementation-artifacts/epic-3-context.md— Technical Decision Z. 43 auf Ist-Zustand (§5.18) aktualisieren
Acceptance Criteria:
- Given einen lebenden Lease-Halter, when eine höhere Generation sichtbar wird, then bleibt seine Lease aktiv; Staleness verlangt bestätigten Abbruch oder abgelaufene Liveness sowie atomare Ownership-Prüfung (AC-1).
- Given eine nachweislich stale Lease, when sie übernommen wird, then gelingt die Übernahme genau einmal, nennt die ersetzte Holder-ID und hinterlässt genau eine aktive Root-Lease (AC-2).
- Given getrackte oder ungetrackte fremde Änderungen im Mutationsbereich, when der Preflight läuft, then folgt er einer eindeutigen Abort-/Protect-Zustandsmaschine und stellt geschützte Bytes nach dem Run vollständig wieder her (AC-3).
- Given einen Fehler nach Mutation oder Staging, when Rollback läuft, then restauriert er explizit aus dem bezeichneten Baseline-Commit sowohl Index als auch Worktree; der Post-Rollback-Diff gegen die Baseline ist leer (AC-4).
- Given einen erfolgreichen Run, when er freigegeben wird, then sind Mutation, zulässiger Log-/Koordinationsnachweis und Release dauerhaft, der aktive Lock ist entfernt, der Worktree ist sauber und der unmittelbar folgende Run besteht den Clean-Input-Guard (AC-5).
- Given
wiki/log.md, when ein Run protokolliert wird, then enthält das kanonische Knowledge Log nur vertragskonforme fachliche Änderungen und notwendige Koordinationsereignisse; Build-, Review-, Story- und Sandbox-Historie liegt außerhalb des Knowledge Bundle (AC-6). - Given ein Lifecycle, when Kill-Point-Tests vor Mutation, nach Mutation, vor Commit und nach Commit laufen, then beweisen sie den jeweils konsistenten Endzustand (AC-7).
Spec Change Log
Design Notes
Der Lifecycle ist der geschlossene transaktionale Rahmen der Koordinations-Dimension: Akquise (§5.11/§5.17) → Preflight/Protect (§5.11 Pkt. 3) → Mutation (§5.9/§5.10/§5.16) → Rollback (§5.13) → durable Release (§5.11 Pkt. 1/§5.17 Pkt. 1 Ref-Delete) → Clean-Input-Guard (Nachfolger-Bedingung). §5.18 ordnet die bestehenden Mechaniken in eine Zustandsmaschine und ergänzt nur die fehlenden Klammern (Liveness/Ownership, Abort-/Protect-Zustandsmaschine, Index+Worktree-Rollback, durable Release + Clean-Input-Guard, kanonisches Log, Kill-Point-Tests).
Kernprinzipien:
- Keine Wanduhr-TTL: Staleness folgt nie aus Kalenderzeit (A0-20), sondern aus committeten Zuständen (Gen-Registry, §5.12) plus bestätigtem Abbruch / abgelaufener Liveness (deterministisch belegt, z. B. Halter-Branch-Verlust/Registry-Status) — Liveness ist ein beobachtbarer, kein zeitlicher Zustand.
- Ownership-Prägung: Akquise (create-only-Existenz, §5.17), Übernahme (atomare Ownership-Prüfung: Inhaber-Run-ID muss Lock-Inhalt tragen) und Release (Ref-Delete nur durch Inhaber) sind einheitlich ownership-gebunden.
- Rollback = Baseline-Punkt: Index + Worktree werden aus
<Baseline-Commit>restauriert (git reset --hard <Baseline-Commit>ist zulässiges Beispiel — deterministisch, ohne Wanduhr); Post-Rollback-Diff leer (§5.13 Pkt. 3 Zustands-Restaurations-Invariante). - Clean-Input-Guard: Nach Release muss ein Folge-Run ohne
INPUT_UNCOMMITTED-Abbruch starten — d. h. sauberer Worktree, kein hängender Lock, geschützte Fremd-Bytes sind restauriert. Kill-Punkt „nach Commit" antizipiert genau diesen Zustand.
Verification
Commands:
bash _bmad-output/implementation-artifacts/sandbox-3-12/run-sandbox.sh-- expected: L-1..L-9 harte PASS, Exit 0, kein Zugriff auf reales Bundle/raw/.grep -n "## 5.18" schema/compiler.mdundgrep -n "Revision 3.7" schema/compiler.md-- expected: §5.18-Überschrift und §8-Revisionslogeintrag vorhanden; bestehende §5.11/§5.12/§5.13/§5.17-Texte unverändert (diff prüft nur additive/berichtigte Zeilen).git diff --stat(Repo-Root) -- expected: nur Story-3.12-Touched-Files (compiler.md, sandbox-3-12, spec, log.md, sprint-status.yaml, deferred-work.md, epic-3-context.md);schema/validator.md/schema/wiki-compiler.md/adapters//raw/ohne Diff (AD-3);git status --porcelain -- wiki/zeigt nurwiki/log.md.
Manual checks (if no CLI):
- Keine Beschreibung nötig — sämtliche Nachweise laufen über die Sandbox (Exit-Code) und additive Diffs.
Suggested Review Order
Design-Intent (normative Instruktion)
- Einstieg: die §5.18-Lifecycle-Sektion — Liveness/Ownership, Abort-/Protect-Zustandsmaschine, Baseline-Rollback Index+Worktree, durable Release + Clean-Input-Guard, kanonisches Log, Kill-Point-Tests (AC-1..7).
- Abgrenzungsklausel — Fugen-Identität §5.11/§5.12/§5.13/§5.17; Anschluss-Sutur §5.17-Pkt.-1-Z. 419 / Pkt.-6-Z. 424 („Lifecycle-Regie Story 3.12").
Lifecycle-Mechanik (Sandbox)
- Abort-/Protect-Zustandsmaschine (getrackt/ungetrackt; byte-identischer Restore) — abgeleitet aus sandbox-3-5-L4, gehärtet als Zustandsmaschine.
- Baseline-Rollback Index+Worktree + Kill-Point-Tests (vor Mutation/nach Mutation/vor Commit/nach Commit; Post-Rollback-Diff leer).
- Liveness/Ownership + stale-Übernahme genau einmal (Gen-Registry §5.12-Mechanik; ersetzte Holder-ID; genau eine aktive Root-Lease).
- Durable Release + Clean-Input-Guard (Lock per Ref-Delete; Worktree sauber; Folge-Run ohne INPUT_UNCOMMITTED-Abbruch).
Status- & Nachweissynchronisation (peripher)
- Revisionsnachweis Story 3.12 in der Laufzeitakte (Verankerung, Sandbox, Abschlussklausel, Erhaltungs-Invariante).
- epic-3-context Z. 43 auf Ist-Zustand nachgeführt; Defer-Homes Story-3.12 in deferred-work.md markiert.
Review Findings
Bmad-code-review Loop 1 (2026-08-21), 4 Layer (blind-hunter/edge-case-hunter/verification-gap/acceptance-auditor). Triage: noch offen — Findings werden nach dem Loop im Spec-Change-Log festgehalten.