Q1 — Does layout traverse the parent/child rune boundary? — ANSWERED
Yes, because there is no boundary to cross. identityTransform (engine.ts:138) dispatches transformRune for every node whose data-rune resolves to a config key, nested ones included, and block-and-layout assembly runs inside that per-rune pass (engine.ts:409). Each rune assembles itself from its own RuneConfig; mapDataNames is flat, so a rune's layout pool is its own direct data-named children and nothing deeper.
Verified in packages/transform/test/child-rune-layout.test.ts (4 cases, added by this item): a theme layout on Track reorders its parts and creates a byline wrapper (.rf-track__byline, no data-section); a wrapper named in sections does get its role, and sections is identity-guarded so a theme cannot add one; Playlist's layout cannot reach into Track.
Consequences, applied to ADR-029:
- Item-level theming is an existing config capability. No engine change, and the implementing spec shrinks.
- Decision 2's proposed
groups channel is redundant and was removed. layout's tag-creating form already groups parts, and the semantic boundary is already emitted as the presence or absence of data-section. - Rune-created and theme-created anonymous wrappers are structurally identical (
Card's own content wrapper has no section role either — cardSections is { media, body }). The output distinguishes semantic from presentational, not rune-authored from theme-authored; the latter is the base-versus-theme contract diff's job, per decisions 3 and 4.
Original framing, and why it was wrong
The question was posed as "Track has its own RuneConfig, so in principle a theme can restructure it — but the layout tree was built by SPEC-081 for intra-rune slots and may not reach into a child rune's root."
That presumed a boundary the engine does not have. Assembly is not a single whole-page walk that must descend into nested runes; it is a per-rune pass that recurses naturally, so "reaching into a child rune" is not something layout ever needs to do. The correct question was whether a child rune gets its own pass — and it does.
Worth noting for the remaining two: the planned method here was refrakt inspect playlist, which needs a built CLI. Driving createTransform from source under vitest answered it in minutes with no build at all, and left a regression test behind.
Q2 — Is the omission channel wired anywhere?
Already answered in the negative and filed as BUG-023: data-meta-rank is specified, styled by four Lumina rules, and emitted by nothing.
What remains for this item is the consequence for ADR-029 decision 5, which names the density/rank channel as the bound on what a theme may omit. If the channel does not exist, the bound is unenforceable and the decision needs either a different bound or a dependency on wiring it.
Method. Decide which, and record it. No new investigation needed beyond BUG-023.
Acceptance Criteria
- Q1 answered with the code path named, and a worked example showing whether a theme-supplied
layout on Track takes effect - Q2 resolved into a decision: either ADR-029 decision 5 gains a dependency on wiring
data-meta-rank, or it adopts a different bound - Q3 answered with the explicit list of runes whose
property= rides on omittable visible nodes, derived from the seo-baseline fixtures - ADR-029's Open questions section is rewritten with the findings, and any decision they contradict is amended rather than left standing
- Findings are recorded even where they confirm the assumption — a verified assumption and an unexamined one should not look alike in the record
Notes
Ordering: Q3 is the one that can change a decision, so do it first if the three are split. Q1 is the one that sizes the follow-up spec. Q2 is bookkeeping on a bug already filed.