Skip to content

Follow-up to #568: orphan→shared-helper unification + fresh/reval traversal merge (needs (A)-divergence coverage first) #577

Closed as not planned

Description

@ivogt

Summary

Follow-up to #568, which was closed when #576 merged. #576 shipped 4 of the 6 internal refactors (middleware merge builder, loader-cache interceptor, cache-hit fresh-loader extraction, parallel-slot component extraction) plus the consumer-facing trie suffix longest-wins fix (#575). Two sub-items remain and were deliberately deferred because they carry real semantic risk that the current test suite does not cover. This issue tracks them with the forensic findings already gathered.

Remaining work

Sub-item 2 — orphan-revalidation calls the shared parallel helper (policy args)

resolveOrphanLayoutWithRevalidation still inlines ~166 lines of parallel-slot resolution instead of calling resolveParallelSegmentsWithRevalidation. Two divergences between the inlined loop and the shared helper (src/router/segment-resolution/revalidation.ts):

Divergence Verdict (forensic) Action
(A) orphan defaultOverride: { value: true } vs main belongsToRoute || isNewParent INTENTIONAL — present since #228, deliberately preserved in #482 with a justifying comment, reachable at belongsToRoute=false, and it avoids the #482 blank-parent-chain-slot staleness bug Carry as an explicit policy arg (e.g. parentChainDefault: "force-render" | "type-derived"). Do NOT normalize — that's a product decision that changes rendered output for parent-chain orphan parallels under non-route parents.
(B) orphan loader-resolve-before-push vs main push-before-loaders DRIFT / cosmetic — provably unobservable (segment tree walk + handle filter discard intra-parent order; loaders memoized by $$id); the orphan order is the one out of parity with fresh.ts Safe to normalize to the shared push-then-loaders order (improves fresh/reval parity).

Sub-item 1 — unify the fresh.ts vs revalidation.ts resolution trees

resolveSegment/resolveOrphanLayout/resolveParallelEntry/resolveLoaders + collectEntryLoaders mirror each other across the two files. The issue's "byte-identical" premise is false: collectEntryLoaders twins differ in the loader call (resolveLoaders vs resolveLoadersWithRevalidation, +8 args) and matchedIds accumulation, and the resolveSegment twins diverge in per-segment revalidate gating + route-handler ordering. So this is a strategy-parameterized traversal, not a literal dedup — higher risk, do it after sub-item 2.

Blocker — coverage must come first

parallel-revalidate-fns-invocation.test.ts (the supposed pin) does not lock either divergence: every orphan case it runs passes belongsToRoute=true (where (A)'s two policies coincide) and the revalidate fns override the seed value. It therefore stays green under any unification and cannot catch a regression in (A) or (B).

Before refactoring, add a pinning test for the divergent (A) case: orphan parallel with belongsToRoute=false, slot ∉ clientSegmentIds, parent ∈ clientSegmentIds (so isNewParent=false), and zero revalidate fns — assert the slot resolves to a non-null component and appears in matchedIds (the orphan force-render behavior; the main path would skip it). Then carry (A) as a policy arg, normalize (B), and re-run the semantic matrix.

Acceptance

  • New (A)-divergence pinning test added and red-before/green-after the policy-arg wiring.
  • Behavior-preserving (matrix rows unchanged), semantic-matrix green, execution-model.md updated if the contract is restated.
  • debugPerformance before/after for the partial-revalidation hot path.

Activity

  1. ivogt commented on Jun 14, 2026

    @ivogt
    CollaboratorAuthor

    Duplicate of #568 (now reopened) — folded the remaining-work breakdown + forensic verdict into #568. Tracking continues there.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions