Co to znamená
.ai/local/prompts/ drží prompty, které člověk skutečně odeslal, zapsané vlastním hookem poskytovatele dřív, než byl model vyvolán, každý uložený dvakrát pod jedním kmenem: záznam .json a jeho vykreslení .md. Repozitář, který deklaruje vynucování, je mu podroben: pokud hook přestane zachytávat, doctor selže, a protože doctor běží na pre-commit, commit se zastaví s ním. Poskytovatel, jehož prompty nelze pozorovat, se hlásí jako unsupported, ne jako takový, který neměl co říct.
Princip
capture install zapíše shim do .claude/hooks/majordomus-capture a položku UserPromptSubmit do .claude/settings.json, přičemž odmítne přepsat kteroukoli z nich — vypíše položku k přidání a skončí kódem 15. Claude Code spustí shim dříve, než model uvidí prompt, a předá mu JSON payload na stdin; mj_capture_prompt v lib/capture.sh jej přečte pomocí lib/json_scan.awk a zapíše jeden záznam jako jeden soubor, .ai/local/prompts/YYYYMMDDHHMMSS-<slug>.json, kde slug je začátek promptu, a vedle něj <same stem>.md — uzavřená množina polí jako YAML front matter, tatáž pole jako tabulka pro člověka a prompt poslední pod ## PROMPT, dekódovaný a ohraničený řadou zpětných apostrofů delší než jakákoli řada uvnitř, aby prompt citující kód nemohl blok předčasně ukončit. Záznam je po zapsání neměnný, dva hooky ve vzájemném souběhu se nemohou prolnout uvnitř jednoho souboru, jména se řadí chronologicky a prompt lze najít vypsáním adresáře.
Skener vrací surový JSON rozsah každého člena nejvyšší úrovně, takže zachycený text je bajt po bajtu shodný s tím, co poskytovatel poslal: neexistuje krok dekódování a znovu zakódování, který by mohl ztratit escape, a payload, který skener nedokáže parsovat, se odmítne celý, ne po částech. Záznamy zůstávají idempotentní na vlastní identitě promptu u poskytovatele, což je pole, ne jméno: hook doručený dvakrát během dne zapíše jednou. Opakované doručení po dnech není případ, který toto tvrzení pokrývá, a kód to říká tam, kde se okno volí.
Formáty jsou dva, protože jeden soubor nemůže být obojí. Záznam je to, co provider poslal a z čeho se vše ostatní odvozuje; escapovaný na jednom řádku není tím, co člověk otevírá. Vykreslení je to, co člověk otevírá; dekódované a přeformátované není tím, z čeho lze znovu sestavit bajtově věrný archiv. Ponechat jen jedno by buď vzdalo důkaz, nebo čtení, takže se při každém zachycení zapisují obě a asymetrie mezi nimi je to, co z dvojice činí vynutitelnou: mj_capture_render_one umí z jeho záznamu znovu sestavit jakékoli vykreslení, ale opačně nic. doctor proto selže na záznamu bez vykreslení a jmenuje majordomus capture render jako nápravu a selže na vykreslení bez záznamu, aniž nabídne nápravu, protože ta polovina je nezotavitelná a smazat ji smí rozhodnout jen člověk.
wired_by: provider-hook:<provider> je druh vynucování a doctor o něm rozhoduje tím, že prožene syntetický payload přes shim do jednorázového archivu a přečte obě poloviny zpět. Proto jsou stavy pět slov, ne dvě: unsupported, unconfigured, named, wired, verified. Deklarované vynucování splňuje jen verified a jen verified znamená, že payload skutečně vyšel na druhé straně.
Zachycení nemůže selhat nahlas, takže selhává do .capture.log vedle záznamů a neprázdný log je blokující selhání, ne poznámka. Je to jediná kontrola, která zachytí podstatné selhání: pokud poskytovatel přejmenuje pole, v němž prompt přichází, hook se pořád spustí a vlastní test prochází, protože vlastní test posílá payload vyrobený samotným nástrojem. Bez logu by se každý prompt ztratil v tichosti.
Archiv nic neořezává. Prompt není přeformulováním stavu drženého jinde, takže jej neomezuje žádný strop a žádný příkaz jej nesmaže jako vedlejší efekt; doctor místo toho hlásí počet a velikost a mazání je záměrný čin člověka.
Doktrína majordomus.prompt-capture drží archiv zvlášť: nic pod ním nesmí být sledováno Gitem, hranice ignorování ho musí pokrývat, každý záznam musí nést uzavřenou množinu polí a každý prompt musí existovat jako záznam i jako vykreslení. Záznam, který uvádí odpověď, dokončení nebo přepis, je selhání, protože archiv drží polovinu výměny patřící člověku a nic víc.
Jak to vidět
majordomus capture status # claude-code unconfigured
majordomus capture install
majordomus capture status # claude-code verified
chmod -x .claude/hooks/majordomus-capture
majordomus capture status # claude-code named — not executable
majordomus doctor # exit 10, FAIL wiring prompt-capture
rm .ai/local/prompts/*.md
majordomus doctor # exit 10, FAIL capture — n record(s) have no Markdown rendering
majordomus capture render # n rendering(s) written into .ai/local/prompts
majordomus doctor # OK capture — every prompt is present as both a record and a renderingCo nepokrývá
Rozsah tvoří prompty odeslané přes zapojený adaptér providera v tomto checkoutu a tímto mechanismem jej nelze rozšířit. Prompty zadané na webu, v desktopové aplikaci, na jiném stroji nebo u providera bez adaptéru nelze pozorovat z hooku, který nikdy neběžel, a žádný se tu neobjeví. Adaptér má jen Claude Code. Otázka, kterou tato věta dříve odkládala — zda mají Codex či Gemini ekvivalentní událost — byla rozhodnuta 2026-09-11 a odpověď je, že oba ano: Codex CLI spouští UserPromptSubmit před voláním modelu a Gemini CLI spouští BeforeAgent, každý předává surový prompt příkazu, každý citovatelný v share/providers.yaml. Jsou tedy unadapted — tato distribuce žádný adaptér nedodává — a ne unsupported, což by byl nepravdivý výrok o jejich produktech (ADR 0103). Zachycení promptu přes spojení MCP není náhrada a je deklarováno jako nemožné: server dostává volání nástrojů, nikdy prompt, který je vyvolal.
Nepokrývá ani vše, co událost doručuje. Claude Code spouští UserPromptSubmit i pro zprávy, které sám vkládá do tahu, a ty se filtrují podle deklarovaného původu a podle značek, jimiž začínají — záměrně, protože to nejsou prompty osoby, ale znamená to, že archiv je to, co filtr propustil, a ne přepis události.
Archiv také není znalost. Nic jej nenačítá do kontextu, žádný příkaz z něj nevyhledává a žádný jej nesumarizuje. Je to důkaz, který člověk může číst, a jediná tvrzení nástroje o něm jsou, že je skutečný, úplný pro to, co pokrývá, a nikdy necommitnutý.
Proč existuje
Adresář byl deklarován protokolem .ai a zůstal prázdný, což se čte jako nefunkční funkce. Zřejmá oprava — řádek v AGENTS.md, který pracovníkovi říká, aby zaznamenával své prompty — jí být nemůže: model nikdy nevidí bajty, které člověk napsal, zápis závisí na tom, že se rozhodne provést volání nástroje, žádný behaviorální test nemůže dokázat, že proběhl, a instrukce se načte teprve poté, co byl první prompt relace už odeslán. .ai/repo/adrs/0009-prompt-capture-happens-below-the-model.md zaznamenává rozhodnutí, které následovalo.