Přeskočit na obsah

Tato stránka byla automaticky přeložena z angličtiny, jediného jazyka, ve kterém se tento web píše. Číst originál.

Rustdoc crate je publikovaný webový povrch na /rustdoc, vytvořený voláním, které dokládá jeho kontrola, a ověřený na veřejné URL

Rustdoc crate je publikovaný webový povrch na /rustdoc, vytvořený voláním, které dokládá jeho kontrola, a ověřený na veřejné URL

majordomus://adr/adr-0086navrženo rustdokumentacewebpublikaceci

odkazuje na

odkazuje na něj

86. Rustdoc crate je publikovaný webový povrch, vytvořený voláním, které jeho kontrola dokazuje, a ověřený na veřejném URL

Kontext

Poslání vlastníka z 2026-09-24 žádalo ExDoc jako plnohodnotnou plochu: generovaná reference API pojatá jako součást uzavření dokumentace, vytvářená, vkládaná, směrovaná, odkazovaná, testovaná, nasazovaná a ověřovaná tam, kde ji čte veřejnost. ExDoc patří Elixiru. Tento repozitář Elixir nemá: je to jeden crate v Rustu, apps/majordomus-cli, skripty v shellu, jq a awk a web v Zole. Ekvivalentem je rustdoc — vlastní dokumentace //! a /// crate vykreslená toolchainem, jedna stránka na exportovanou položku, se zdrojem, ze kterého byla stránka postavena.

Kvalita toho, co by se publikovalo, už vlastníka měla. #![warn(missing_docs)] v lib.rs s -D warnings v kontrole činí nezdokumentovaný export selháním sestavení a project.rust-public-api-quality (ADR 0028) měří příklady a řídkou dokumentaci ze syntaktického stromu crate, ráčnovanou .ai/repo/rust-quality-baseline.txt. Co chybělo, nebyla dokumentace. Byla to každá fáze po rendereru. Audit z 2026-09-24:

  • Výstup byl zahozen. cargo doc běžel jen jako kontrola — krok cargo doc -D warnings v scripts/rust-check, RUSTDOCFLAGS='-D warnings' cargo doc --no-deps --quiet — a nikdo nečetl, co zapsal. Kontrola při každém běhu dokazovala, že se reference vykreslí bez varování, a ani jeden čtenář ji nemohl otevřít.
  • Žádný povrch to nedeklaroval. web::discover znalo trasy spustitelného souboru, web a generované zprávy pod target/web/; strom rustdoc nebyl žádným z nich, takže ho router nemohl servírovat, domovská stránka na něj nemohla odkazovat a docs/generated/web.json ho nejmenovalo.
  • Žádný krok webu to nenesl. scripts/site-build sestavil Zolu do site/public a nic jiného tam nešlo.
  • Publikační úloha neměla Rust. .github/workflows/pages.yml instaluje Node a Zola; strom by nedokázala vytvořit, ani kdyby byla požádána.
  • Ověření to nevidělo. scripts/pages verify čte /build.json a nic jiného, takže nasazení, které ztratilo celý podstrom, by prošlo ověřením.
  • Žádná identita nespojovala položku se stránkou. Nic nemohlo říct „tato exportovaná položka nemá stránku“, protože nic nemapovalo položku na route, kterou jí rustdoc dává.
  • Naživo každá kandidátní trasa odpověděla 404 na https://majordomus.dev.

To je selhání, které ADR 0013 popisuje pro plochu známou na šesti místech, o krok dál: tady ji neznalo žádné místo a jediná kontrola, která se jí dotkla, dokázala vlastnost artefaktu, který pak zahodila. Úspěšné generování se implicitně četlo jako existence reference.

Rozhodnutí

Rustdoc crate je webový povrch s id rustdoc, připojený na /rustdoc, dostupný v obou světech — servírovaný majordomus serve a publikovaný na https://majordomus.dev/rustdoc/ — a každá fáze mezi zdrojem a veřejnou URL je rozhodována spustitelnou kontrolou. project.the-crate-reference-is-published je pravidlo; docs/RUSTDOC.md je provozní dokument.

fázeco platírozhodl
zdrojkaždá exportovaná položka je zdokumentována; příklady podle quality ratchetucargo doc -D warnings, kontrola rust-quality
generováníjeden producent, vlastní vyvolání kontrolyscripts/rust-check --doc; případ 77 drží jediné volání
vkládánípovrch deklarovaný zjišťováním, nezávislý na checkoutumajordomus web validate, generate --check
routing/rustdoc/ servírováno ze stromu, publikováno na stejném mountuweb::files, router, případ 488
referenceskaždá exportovaná položka má svou stránku, žádná sirotčí, interní odkazy se rozlišujímajordomus quality rustdoc, scripts/ci/link-check
nasazenístrom složený z topologie, nikdy necommitovaný, sestavený z commitu builduscripts/site-build, scripts/site-check sekce 13m, scripts/site-deploy, případy 486 a 489
ověření nasazeníveřejná reference jmenuje nasazený commit a je úplnáscripts/pages verify-rustdoc, kontrola pages-live, případ 487

Vlastní mount na nejvyšší úrovni

/rustdoc, ne cesta pod existujícím jmenným prostorem. /docs patří obsluhovanému povrchu docs a web::validate odmítne vnořený mount, který vnější povrch nedeklaroval; /api by seděl nad /api/v1, routes schopností; „reference“ zde už jmenuje několik věcí (scripts/ci/reference-check, /docs/api/, /docs/cli/ a /registry/). Povrch je pojmenován po svém producentovi, stejně jako swagger.

Deklarováno objevením z cratu

Povrch se deklaruje objevením z crate samotného, stejně jako se docs deklaruje z site/config.toml: je v topologii, kdykoli je crate, ať už producent v tomto checkoutu běžel, nebo ne. Topologie, domovská stránka a commitnutá docs/generated/web.json tedy nikdy nezávisejí na tom, že proběhl build. Průchod přes target/web/ přeskakuje adresář rustdoc stejně jako docs, built_from se čte z surface.json producenta a commitnutá projekce ho vynechává přesně tak, jako vynechává build dokumentace, protože hodnota lišící se podle checkoutu by způsobila, že každý klon hlásí drift.

Producentem je vlastní vyvolání kontroly

scripts/rust-check --doc spouští krok cargo doc -D warnings — tentýž řádek, který běží v režimech full a CI, ne druhou variantu — a předává jeho výstup: stránky se kopírují z adresáře, který cargo hlásí jako svůj target, do target/web/rustdoc/, vedle surface.json (web-surface/v1: id, mount, název, producent, dostupnost both, kategorie documentation, viditelnost public, built_from HEAD checkoutu) a přistávací index.html, protože rustdoc zapisuje index pro každý crate a žádný v kořeni. Stránka knihovního cratu je /rustdoc/majordomus_cli/index.html.

Dokumentuje se veřejné položky knihovny a spustitelný soubor, se zachovanými vlastními zdrojovými stránkami rustdocu. Reference sestavená jiným voláním, než jaké kontroluje kontrola, je druhý artefakt, který nikdo nedoložil, takže existuje jeden řádek cargo doc a případ 77 selže na druhém. --document-private-items se nepředává: ADR 0028 rozhoduje, co je veřejný povrch knihovny, a publikování soukromého by tvrdilo opak. Spustitelný soubor je dokumentován tak, jak cargo dokumentuje jakýkoli binární cíl — s vlastními položkami, protože binárka nic neexportuje — což je dnes jeho main a nic jiného. Zdrojové stránky jsou zdroj přesně v commitu, ze kterého byl strom sestaven, což je nejsilnější zdrojový odkaz, jaký reference může nést.

Necommitnuto; generováno v CI a dokázáno jako čerstvé

Strom producenta měřil 2026-09-24 u f7e05f4c5 81 MB ve 3083 souborech — stránky, které rustdoc zapsal, úvodní stránka a surface.json, sečteno podle velikosti v bajtech — a stránky vkládají hodnoty konstant COMMIT a GENERATION crate: rustdoc vykresluje pub const COMMIT: &str = "<forty hex digits>"; na stránce konstanty. Commitnutý by strom byl zastaralý při každém commitu, který se crate dotkl, a skrze tu jednu stránku při každém commitu vůbec, a vložil by celou svou velikost do každého klonu. Místo toho se generuje v CI: vlastní úlohou rustdoc v pages.yml, ne kroky úlohy nasazení, která strom předává úloze nasazení jako artefakt téhož běhu; a úlohy validačního workflow, které web sestavují, ho získávají stejnou složenou akcí, .github/actions/rustdoc, takže oba workflow ho nemohou sestavit odlišně. Úloha nasazení potřebuje úlohu rustdoc, takže běží jedna po druhé: sestavení webu skládá strom a kontroly webu posuzují složený výstup, takže ani jedno nemůže začít dřív, než strom existuje.

Čerstvost má dva svědky, kteří nesdílejí zapisovatele. built_from v surface.json je výrok výrobce o commitu; vlastní stránka crate pro jeho konstantu COMMIT je to, co kompilátor vložil při sestavení stránek. Oba musí jmenovat kontrolovaný commit a veřejné ověření čte oba.

Druhý svědek má předpoklad. COMMIT je to, co build.rs přečetl při posledním běhu, a build.rs deklaruje jeho opětovná spuštění: zdroje crate, jeho manifest, jeho lock soubor a MAJORDOMUS_BUILD_COMMIT — ne HEAD. Po commitu, který se nedotkne ničeho z toho, je prosté cargo doc čerstvé, rustdoc neběží a stránka s konstantou stále jmenuje dřívější commit, zatímco producent, který čte HEAD, zaznamená nový. To bylo změřeno 2026-09-24 s rustdoc 1.98.1 na testovacím crate nesoucím stejné deklarace opětovného spuštění. Producent proto předá sestavení commit, který zaznamenává — MAJORDOMUS_BUILD_COMMIT, což build.rs už respektuje — a oba svědci se zapisují z jedné hodnoty jedním sestavením. Dva svědci, kteří se neshodují, pak znamenají jedno: strom byl složen ze dvou sestavení.

Kompozice se odvozuje z topologie

scripts/site-build kopíruje každý publikovaný statický povrch jiný než samotný web do svého výstupu na připojení povrchu, přičemž seznam čte z docs/generated/web.json. Nenachází se v něm žádný řádek jmenující rustdoc: povrch přidaný zítra se složí zítra. Publikovaný povrch, jehož artefakt chybí, odmítne build s exit 12 a jmenuje producenta, který jej zapisuje, takže web nelze publikovat bez povrchu, který topologie říká, že nese. Připojení, které web sám už plní, se odmítne s exit 10, místo aby bylo přepsáno: jedna cesta má jednoho vlastníka. Build zaznamenává každý složený povrch s commitem, který deklaroval jeho producent, pod surfaces v /build.json a scripts/site-check (sekce 13m) odmítne složený povrch, který chybí, nenese deklaraci, deklaruje jiné id nebo připojení než topologie nebo byl sestaven z jiného commitu než build.

Výběr je jeden pomocník, mj_web_composed v lib/common.sh, nad commitnutým web.json: každý povrch druhu statický adresář, který publikace nese, kromě webu. Build, který skládá, i každá kontrola, která musí odlišit stránky webu od složeného povrchu, se ho ptají, takže žádný skript nejmenuje mount.

Stránky každého povrchu posuzuje kontrola tohoto povrchu

Smlouva stránek webu — orientační body, metadata, žádný inline styl, návrhové tokeny — posuzuje stránky, které Zola vykresluje. Stránky pod připojením jiného povrchu, odvozené z web.json, jsou z této smlouvy vyjmuty, protože markup rustdoc patří toolchainu a žádná zdejší šablona ho nezmění; posuzuje je místo toho majordomus quality rustdoc. Odkaz ze stránky webu do /rustdoc/ rozhoduje scripts/ci/link-check proti složenému stromu jako každý jiný vnitřní soubor.

Kontrola integrity se připojuje ke kanonickému inventáři

majordomus quality rustdoc [--tree DIR], schopnost quality.rustdoc, je Rust a čte vykreslený strom proti quality::source::Inventory — měření exportovaných položek crate, které už používá project.rust-public-api-quality. Vyžaduje, aby každá exportovaná položka měla svou stránku na trase odvozené z její cesty a druhu, aby neexistovala stránka položky bez položky, aby se strom přihlásil sám a jeho built_from byl HEAD, aby index crate nesl svou identitu (<title>majordomus_cli - Rust</title>), aby aktiva indexu byla přítomná, aby interní odkazy fungovaly a aby žádná stránka neuváděla cestu stroje ani tajemství. Končí 0 čistý, 10 s nálezy a 12, když není strom k posouzení — nikdy prázdný průchod. Inventář není seznam vedený pro tohoto konzumenta: je to crate, které měří samo sebe, a trasy se z něj odvozují konvencí samotného toolchainu. Stránky programu se posuzují týmž průchodem nad inventářem vlastního cílového binárního targetu.

Veřejné ověření je vynuceno

scripts/pages verify-rustdoc --commit SHA [--url URL] [--timeout N] je samostatná funkce vedle verify, ne její rozšíření. Běží jako tvrdý krok pages.yml, jakmile web obsluhuje nasazený commit, a jako sekce scripts/ci/pages-check, kontroly pages-live. Nasazení, jehož veřejná reference chybí, je rozbitá nebo sestavená z jiného commitu, selže.

To je záměrná výjimka z principu, že nic změřeného po pushi do gh-pages se nestane verdiktem běhu (docs/GITHUB_PAGES_PERFORMANCE.md), a je to v souladu s důvodem tohoto principu. Princip existuje proto, že překročení latence u nasazení, které proběhlo, není neúspěšné nasazení. Odkaz, který je na své veřejné URL rozbitý, jím je — stejná kategorie jako chyba vlastního buildu gh-pages na GitHubu, který ten workflow už červeně označuje.

Co se nemění

Politika pokrytí. Nevymýšlí se žádný práh: missing_docs s -D warnings už vyžaduje, aby byla zdokumentována každá exportovaná položka, a ratchet rust-quality hlídá příklady a tenkou dokumentaci. quality rustdoc hlásí počty, které spojuje, a nežádá nic, co stávající politika nežádá.

Kontrakt. Publikace rustdoc nedělá z Rust API crate příslib kompatibility. Crate je publish = false a ADR 0051 měří veřejný kontrakt z registru schopností. Úvodní stránka to říká slovy.

Zamítnuté alternativy

Commitnout strom. Jeho velikost a konstanty, které vkládá, z něj dělají soubor, který zastará v okamžiku, kdy se crate pohne, a zátěž každého klonu, který ho nikdy nečte. Commitnutý strom je také jeden další odvozený artefakt, u kterého je třeba dokazovat aktuálnost, když ji nasazený commit a stránka konstant dokazují příměji.

Připojit ho na /docs/rust. /docs patří servírované dokumentaci a vnořené připojení, které vnější povrch nedeklaroval, odmítá web::validate i konstrukce routeru. Deklarace vnoření by sestavení webu dala díru, o které jeho vlastní zdroj neví, a umístila by referenci do jediného jmenného prostoru, o který už tento repozitář jednou bojoval.

majordomus web compose na cestě nasazení. Skládá se z vyřešené topologie a je správným nástrojem tam, kde je spustitelný soubor po ruce, ale publikační job nenese toolchain Rustu a neměl by stavět spustitelný soubor jen kvůli kopírování adresářů. site-build čte commitnutý web.json, což je totéž rozlišení, které už promítá a na drift kontroluje generate --check, takže se nic nerozhoduje dvakrát.

Výstup JSON z rustdoc jako inventář. --output-format json je nestabilní a vyžaduje nightly toolchain; tento repozitář připíná stabilní v rust-toolchain.toml. Byl by to také druhý běh rustdoc a kontrola by pak posuzovala jiný běh, než jaký publikuje. Vlastní inventář syntaktického stromu crate je stabilní a už je mírou veřejného povrchu.

--document-private-items. Publikuje to, co ADR 0028 rozhodlo, že povrchem není, a způsobilo by to, že sada vykreslených položek by neodpovídala inventáři, se kterým ji kontrola spojuje.

cargo doc uvnitř úlohy deploy. Vkládá instalaci toolchainu Rustu, build cache crate a sestavení dokumentace do úlohy, jejíž fáze .ai/repo/ci/pages.yaml rozpočtuje, v sérii s každou z nich. Samostatná úloha není rychlejší — úloha deploy ji potřebuje, takže obě stále běží v sérii — ale drží toolchain Rustu a jeho build cache mimo úlohu deploy, klíčuje tuto cache vlastní úlohou, takže obnovuje cache sestavení dokumentace, ne validačního workflow, dělá z ceny reference samostatný řádek v měřené publikaci a spouští stejnou akci, jakou spouští validační workflow.

Samostatný skript verifikátoru. Nová shellová jednotka pro jednu funkci, která patří vedle verify, čte stejný model a sdílí jeho polling. verify-rustdoc je podpříkaz scripts/pages a kontrola jej čte přes pages-check, nikoli přes druhý vstupní bod.

Důsledky

  • gh-pages roste jednou o strom, pak o jeho rozdíly. První nasazení přidá do větve celý strom — kolem 81 MB při výše uvedeném měření, než git zkomprimuje; další přidávají, co se změnilo — stránky změněných položek, konstantní stránky, vyhledávací index, úvodní stránku. Nezměněné stránky jsou tytéž bloby, takže je git uloží jednou. scripts/site-deploy stahuje jedinou větev, kterou pushuje, a tento fetch roste s ní.
  • Publikace čeká na referenci. Úloha nasazení potřebuje úlohu rustdoc, takže čas od pushe k zveřejnění roste o celou dobu trvání této úlohy, stažení jejího stromu a frontu GitHubu mezi oběma úlohami. Podíl reference je samostatný řádek mezi fázemi, které úloha nasazení měří — doba běhu úlohy a stažení — a fronta mezi úlohami se hlásí jako queue, protože je GitHubova. Měří ji běh, který ji platí, ne odhad zde; .ai/repo/ci/pages.yaml rozpočtuje řízené fáze a řádek, který nejmenuje, se posoudit nedá.
  • Posun toolchainu může přesunout trasy. Rozložení rustdocu, názvy jeho statických souborů a konvence tras patří toolchainu. Zvýšení pinu v rust-toolchain.toml je může změnit a quality rustdoc selže dřív, než veřejnost uvidí rozbitou stránku; odvození tras se opraví ve stejné změně jako posun.
  • Předmět link-check se mění. Nyní rozhoduje o odkazech ze stránek webu do /rustdoc/ proti složenému stromu a neprochází samotné stránky rustdoc, jejichž vnitřní odkazy rozhoduje quality rustdoc. Jeho jmenovatelem jsou stránky webu a říká to.
  • Build webu potřebuje artefakt každého publikovaného povrchu. Lokálně scripts/site-build odmítne běžet, dokud neproběhne scripts/rust-check --doc (nebo just rustdoc), a ten příkaz jmenuje. V CI každá úloha, která web buildí, nejprve získá strom.
  • Zdrojové soubory crate mohou změnit publikované bajty. Změna crate mění referenci, takže cesty, které spouštějí publikaci, musí zahrnovat to, co ji vytváří: zdrojové soubory crate, manifest, lock soubor a build skript, pin toolchainu, producenta a jeho akci. Odvozuje je, stejně jako každou spouštěcí cestu, scripts/pages paths z modelu kontrol a modelu publikace a nikdy se nepíší do workflow; případ 97 drží spouštěč workflow u tohoto odvození. Spouštěč, který je vynechá, nechá veřejnou referenci na posledním nasazení, zatímco master jde dál, a nic to nehlásí jako dlužné, protože kontrola pages-live rozhoduje, co je dlužné, ze stejných cest.

Odkud to pochází

kanonický soubor
.ai/repo/adrs/0086-the-crates-rustdoc-is-a-published-surface-produced-by-its-gate-and-verified-live.md
identity
adr-0086
dostupné také jako
Zdroj MCP majordomus://adr/adr-0086 · majordomus entity show adr/adr-0086 · GET /api/v1/entity?uri=majordomus://adr/adr-0086
v Cockpitu
/cockpit/objects/adr/adr-0086

Tato stránka je generována z výše uvedeného souboru pomocí scripts/generate-site-data; úprava stránky nic nemění, úprava souboru změní všechna rozhraní. Výše uvedené vztahy jsou hrany docs/generated/graph.json, které spustitelný program zapisuje ze stejného indexu.

Prohledává názvy a popisy všech stránek, které tento web publikuje.