- Define the fragment-rendering convention: render targets are registered templates composing partials; partials are composition units (core.md, emit.md posture B) - Define template kind; trim/restage inline rationale with ADR citations (core.md) - Amend ADR-008: wgsl set ownership resolved engine-owned via OQ-05's 2026-11-06 resolution - Add OQ-09: consolidate the untracked bast-rust-codecs detailed-spec residue (projection, error shape, writer survey) with paired tracker task - Fix oq-05 tracker name to match the corrected unblocking condition - Add reviewed-transition rule: deferred OQs with tracker tasks do not block reviewed; flip six spec docs draft -> reviewed Verification: taskgraph validate (8 tasks valid), em-dash grep zero hits, cargo doc --no-deps clean
6.4 KiB
status, last_updated
| status | last_updated |
|---|---|
| reviewed | 2026-11-06 |
alkgen Architecture: Emit Postures
What and why
A template set renders text; an emit posture is how that text reaches its consumer. The three postures correspond to the three real consumers, and the differences between them are the honest answer to "what differs per target": not the render machinery, but where the text goes and what obligations follow.
ADR-001 demoted the dev-tool from "the product" to one posture among three. This document specifies all three: posture A (build-time static emit), posture B (in-process runtime render), and posture C (render-to-compile feed, future).
Posture A: build-time static emit
Used by the BAST codec template set and its future siblings (call-protocol handlers; branch numbering per phase 0: branches 1 and 2).
- Consumer: a downstream project's build script. alkgen is a generator dependency of the build, not a runtime dependency of the generated output (ADR-007: generated code is zero-dependency; phase-0 OQ-GN-06).
- Output unit: module-level files (phase-0 OQ-GN-01 resolution): one document produces one or more self-contained modules dropped into the consumer's source tree. Crate and fragment generation are out for v1. Partitioning, regeneration, and validation policies are per-target decisions (OQ-01, OQ-02, OQ-03), not core or posture-A-wide policy (ADR-001); posture A fixes only the invariants above: banner, determinism, convention-conformant generated code, and the no-filesystem-in-library rule that makes the core wasm-clean (ADR-003, convention 4): rendering returns text and the consumer's build script owns file placement.
- Output hygiene, because files get checked in (AGENTS.md
convention 8):
- every artifact starts with the "Auto-generated by alkgen. DO NOT EDIT." banner;
- rendering is deterministic, so regeneration is diff-quiet: same document, same templates, same options produce byte-identical files;
- generated code is convention-conformant: no panics on input (error-returning), no unsafe, no dependence on alktype.
- Integration shape: the build script calls the API directly (documented pattern; the reader POC validated the build.rs shape end-to-end, finding F-4). No CLI exists in v1 (ADR-010).
Posture B: in-process runtime render
Used by SSR consumers, currently alkforge (ADR-006).
- Consumer: alkforge links alkgen as a library and renders HTML on demand: per request, or cached by the consumer and re-rendered on content change. The choice between eager cache and render-per-request is alkforge's; determinism of rendering is what makes consumer-side caching safe to build (ADR-003).
- Output unit: fragments and full pages. Partials make fragments natural; pages compose fragments (ADR-006). Render targets are registered templates composing partials (core.md); a fragment a consumer serves directly is registered as its own template. The phase-0 fragment exclusion (OQ-GN-01) was scoped to posture A and does not apply here.
- Output hygiene: rendered HTML is the product, not a checked-in generated artifact, so the DO-NOT-EDIT banner does not apply. Determinism still applies (caching, hashing, and alkforge's render tests all lean on it), and alkforge's page templates are pinned by golden render tests in alkforge, per the templates-are-code convention.
- Assets: alkforge page templates live in alkforge and register into a core-built registry (ADR-008). alkgen ships no HTML assets for posture B beyond the registry API itself; the open question about generic layout primitives is OQ-07.
- Errors: render failure is a typed error mapped by the consumer to its error surface (an alkforge error page). No panics; alkforge serves hostile traffic (AGENTS.md convention 2).
- Performance: alkforge owns its latency budget; the architecture obligation here is only the shape that keeps it achievable: pure, cheap, repeated rendering with no hidden I/O. The reader POC's numbers are research data for the codec target, not acceptance thresholds for this posture; page-template budgets are set by alkforge's web design when it exists.
Posture C: render-to-compile feed
Future (branch 3, template-JIT; OQ-06). The render step is the JIT step: alkgen renders shader (WGSL) text, and downstream compiles and caches the compiled artifact, exactly the alkminer-v1 ShaderBuilder shape.
- Nothing new is required from the core today. The posture-critical properties were fixed up front because retrofitting them is costly: partials are first-class (core.md), rendering is pure, synchronous, and deterministic (ADR-002, ADR-003), and output carries no banner or file-system assumptions. ADR-010's library-only rule also applies: the wasm-bound alkjs runtime uses the library, not a tool.
Cross-posture obligations
| Obligation | A | B | C |
|---|---|---|---|
| Deterministic byte-identical output | yes | yes | yes |
| Typed errors, no panics | yes | yes | yes |
| DO-NOT-EDIT banner | yes | no | no |
| Golden render tests pin output | yes | yes (in owning crate) | yes |
| Validity pinning by template set | yes | yes | yes |
The last row is the general rule (ADR-001): each template set's render tests pin what "valid output" means for it. The core cannot know and must not pretend to: WGSL syntax, HTML well-formedness, and Rust compilability are property tests owned by each set, not core concepts.
Design Decisions
All design decisions are documented as ADRs in decisions/.
| ADR | Decision | Summary |
|---|---|---|
| 003 | Sync, wasm-clean, deterministic | Underwrites caching and hashing in every posture |
| 006 | In-process SSR library | Posture B's shape for alkforge |
| 007 | Typed direct codecs | Posture A's generated-code contract |
| 010 | Library-only v1 | Build-script integration, no CLI |
Open Questions
Open questions are tracked in open-questions.md. Key questions affecting this document:
- OQ-01: file partitioning policy for posture A artifacts (deferred(scope), per-target)
- OQ-02: regeneration posture for posture A artifacts: wholesale overwrite vs alternatives that allow hand-edited code (deferred(scope), per-target)
- OQ-06: template-JIT core requirements (deferred(scope))