[PR #1088] [MERGED] refactor(app-router): fence AppElements wire-key construction #1084

Closed
opened 2026-05-06 13:11:53 +02:00 by BreizhHardware · 0 comments

📋 Pull Request Information

Original PR: https://github.com/cloudflare/vinext/pull/1088
Author: @NathanDrake2406
Created: 5/6/2026
Status: Merged
Merged: 5/6/2026
Merged by: @james-elicx

Base: mainHead: nathan/726-wire-02-03


📝 Commits (2)

  • 1f66bd7 refactor(app-router): fence AppElements wire-key construction
  • 98c6609 refactor(app-router): address AppElements wire review

📊 Changes

9 files changed (+276 additions, -38 deletions)

View changed files

📝 packages/vinext/src/build/layout-classification.ts (+4 -1)
📝 packages/vinext/src/server/app-elements-wire.ts (+99 -10)
📝 packages/vinext/src/server/app-elements.ts (+6 -5)
📝 packages/vinext/src/server/app-page-dispatch.ts (+4 -2)
📝 packages/vinext/src/server/app-page-route-wiring.tsx (+4 -4)
📝 packages/vinext/src/shims/slot.tsx (+13 -4)
📝 tests/app-elements.test.ts (+138 -6)
📝 tests/app-page-element-builder.test.ts (+2 -2)
📝 tests/prefetch-cache.test.ts (+6 -4)

📄 Description

What this changes

Implements task #726-WIRE-02/03 from issue #726 by moving AppElements wire-key construction and parsing behind AppElementsWire.

The codec now owns constructors and parsers for route, page, layout, template, slot, cache, metadata, and unmatched-slot wire values. Render wiring, layout classification, browser slot merging, mounted-slot header construction, and prefetch cache tests now call the codec instead of assembling or recognizing raw layout:, page:, template:, or slot: keys directly.

Why

Issue #726 calls out that the flat AppElements payload should stay as the transport, but raw wire keys must stop becoming router authority. Before this change, several code paths still constructed or interpreted wire keys with string templates or prefix checks outside the wire boundary, which made it easy for future router work to rebuild semantics around incidental payload strings.

Correctness oracle: Vinext internal invariant from #726. The wire format remains byte-compatible for existing payload keys and legacy metadata behavior, but ownership moves to AppElementsWire.

Approach

  • Added AppElementsWire constructors for layout, template, and slot element IDs, plus an element-key parser and slot-key predicate.
  • Kept route graph semantic ID minting separate from the AppElements wire boundary, because graph IDs are route graph facts, not the transport codec.
  • Made direct route/cache helper constructors private so callers use the codec object as the approved exported boundary.
  • Added source-boundary coverage that rejects new raw AppElements wire-key construction outside server/app-elements-wire.ts and routing/app-route-graph.ts.

Non-goals:

  • Does not promote route topology, slot preservation, cache authority, or NavigationPlanner semantics.
  • Does not change the flat payload shape or legacy key strings.

Bonk: please read issue #726 before reviewing this PR so the big-picture AppElementsWire boundary and router-spine migration context is visible.

Validation

  • vp test run tests/app-elements.test.ts tests/prefetch-cache.test.ts tests/app-page-element-builder.test.ts tests/slot.test.ts tests/app-page-route-wiring.test.ts tests/layout-classification.test.ts tests/app-browser-entry.test.ts tests/app-page-render.test.ts tests/app-page-execution.test.ts
  • vp check exits 0. It still reports the existing unrelated typescript-eslint(no-redundant-type-constituents) warning in packages/vinext/src/server/request-pipeline.ts:604.
  • Commit hook ran vp check --fix and knip --no-progress successfully.

Risks / follow-ups

The parser deliberately recognizes the existing legacy wire strings and rejects malformed keys as non-wire entries. Future #726 work can build stronger semantic IDs and planner decisions on top of this without relying on missing payload entries or raw key prefixes as proof.


🔄 This issue represents a GitHub Pull Request. It cannot be merged through Gitea due to API limitations.

## 📋 Pull Request Information **Original PR:** https://github.com/cloudflare/vinext/pull/1088 **Author:** [@NathanDrake2406](https://github.com/NathanDrake2406) **Created:** 5/6/2026 **Status:** ✅ Merged **Merged:** 5/6/2026 **Merged by:** [@james-elicx](https://github.com/james-elicx) **Base:** `main` ← **Head:** `nathan/726-wire-02-03` --- ### 📝 Commits (2) - [`1f66bd7`](https://github.com/cloudflare/vinext/commit/1f66bd77e62bb490553396213cac17bbf7a44768) refactor(app-router): fence AppElements wire-key construction - [`98c6609`](https://github.com/cloudflare/vinext/commit/98c6609cfa1c5b49b737a8ca85d7a718aec45730) refactor(app-router): address AppElements wire review ### 📊 Changes **9 files changed** (+276 additions, -38 deletions) <details> <summary>View changed files</summary> 📝 `packages/vinext/src/build/layout-classification.ts` (+4 -1) 📝 `packages/vinext/src/server/app-elements-wire.ts` (+99 -10) 📝 `packages/vinext/src/server/app-elements.ts` (+6 -5) 📝 `packages/vinext/src/server/app-page-dispatch.ts` (+4 -2) 📝 `packages/vinext/src/server/app-page-route-wiring.tsx` (+4 -4) 📝 `packages/vinext/src/shims/slot.tsx` (+13 -4) 📝 `tests/app-elements.test.ts` (+138 -6) 📝 `tests/app-page-element-builder.test.ts` (+2 -2) 📝 `tests/prefetch-cache.test.ts` (+6 -4) </details> ### 📄 Description ## What this changes Implements task `#726-WIRE-02/03` from issue #726 by moving AppElements wire-key construction and parsing behind `AppElementsWire`. The codec now owns constructors and parsers for route, page, layout, template, slot, cache, metadata, and unmatched-slot wire values. Render wiring, layout classification, browser slot merging, mounted-slot header construction, and prefetch cache tests now call the codec instead of assembling or recognizing raw `layout:`, `page:`, `template:`, or `slot:` keys directly. ## Why Issue #726 calls out that the flat AppElements payload should stay as the transport, but raw wire keys must stop becoming router authority. Before this change, several code paths still constructed or interpreted wire keys with string templates or prefix checks outside the wire boundary, which made it easy for future router work to rebuild semantics around incidental payload strings. Correctness oracle: Vinext internal invariant from #726. The wire format remains byte-compatible for existing payload keys and legacy metadata behavior, but ownership moves to `AppElementsWire`. ## Approach - Added `AppElementsWire` constructors for layout, template, and slot element IDs, plus an element-key parser and slot-key predicate. - Kept route graph semantic ID minting separate from the AppElements wire boundary, because graph IDs are route graph facts, not the transport codec. - Made direct route/cache helper constructors private so callers use the codec object as the approved exported boundary. - Added source-boundary coverage that rejects new raw AppElements wire-key construction outside `server/app-elements-wire.ts` and `routing/app-route-graph.ts`. Non-goals: - Does not promote route topology, slot preservation, cache authority, or NavigationPlanner semantics. - Does not change the flat payload shape or legacy key strings. Bonk: please read issue #726 before reviewing this PR so the big-picture AppElementsWire boundary and router-spine migration context is visible. ## Validation - `vp test run tests/app-elements.test.ts tests/prefetch-cache.test.ts tests/app-page-element-builder.test.ts tests/slot.test.ts tests/app-page-route-wiring.test.ts tests/layout-classification.test.ts tests/app-browser-entry.test.ts tests/app-page-render.test.ts tests/app-page-execution.test.ts` - `vp check` exits 0. It still reports the existing unrelated `typescript-eslint(no-redundant-type-constituents)` warning in `packages/vinext/src/server/request-pipeline.ts:604`. - Commit hook ran `vp check --fix` and `knip --no-progress` successfully. ## Risks / follow-ups The parser deliberately recognizes the existing legacy wire strings and rejects malformed keys as non-wire entries. Future #726 work can build stronger semantic IDs and planner decisions on top of this without relying on missing payload entries or raw key prefixes as proof. --- <sub>🔄 This issue represents a GitHub Pull Request. It cannot be merged through Gitea due to API limitations.</sub>
BreizhHardware 2026-05-06 13:11:53 +02:00
Sign in to join this conversation.
No milestone
No project
No assignees
1 participant
Notifications
Due date
The due date is invalid or out of range. Please use the format "yyyy-mm-dd".

No due date set.

Dependencies

No dependencies set.

Reference
starred/vinext#1084
No description provided.