Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -27,7 +27,9 @@ wire, and the draft do not change here.

Decided 2026-11-11 (maintainer, /quest-plan after #8487's two adversarial
reviews, revised the same day once the first plan's rule was tried on the
router).
router). Moved here from the routes epic the same day (maintainer): the epic
and m2 wait on m1 quests this needs nothing from, it changes tests only, and
the m1 model quests wait on its outcome.

Why: today a relay believes a neighbour's copy of a publisher's claims only
while that neighbour is "feasible", which means strictly cheaper than the
Expand Down
4 changes: 2 additions & 2 deletions quest/m2/cache-routing-proof.md
Original file line number Diff line number Diff line change
Expand Up @@ -30,7 +30,7 @@ second trip to the maintainer for choosing lite-07.
Reopened 2026-11-11 (maintainer, /quest-plan on the route redesign, epic
Plan item 8): a warm route propagates, and the rule that keeps it free of
loops and stale copies is
[the prototype](/quest/m2/cluster-routing/routes/stale-copies.md)'s to pick.
[the prototype](/quest/m1/route-stale-copies.md)'s to pick.
The eligibility rule and the fixtures below are for the one-hop warm route
first decided, which [moq-dev/moq#8457](https://github.com/moq-dev/moq/pull/8457)
proves. Once the prototype's pick is recorded, rewrite both for it: the
Expand Down Expand Up @@ -82,7 +82,7 @@ extension and record the choice and its reason in the epic's Plan.

## Required

- [A prototype settles what keeps a route free of stale copies](/quest/m2/cluster-routing/routes/stale-copies.md) - the rule a propagating warm route rests on, which replaces the one this proved
- [A prototype settles what keeps a route free of stale copies](/quest/m1/route-stale-copies.md) - the rule a propagating warm route rests on, which replaces the one this proved

## Related

Expand Down
2 changes: 1 addition & 1 deletion quest/m2/cluster-routing/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -40,7 +40,7 @@ Decided with the maintainer, 2026-10-13:
Reopened 2026-11-11 (maintainer, /quest-plan after
[moq-dev/moq#8487](https://github.com/moq-dev/moq/pull/8487)'s reviews):
whether Babel's distance stays is
[the prototype](/quest/m2/cluster-routing/routes/stale-copies.md)'s to
[the prototype](/quest/m1/route-stale-copies.md)'s to
measure, against paths alone with a withdrawal that names the hop that
died. The distance refuses a longer way round until the publisher advances
its seqno, and refuses a cached copy at a neighbour no closer to the
Expand Down
2 changes: 1 addition & 1 deletion quest/m2/cluster-routing/routes/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -43,7 +43,7 @@ The items below were decided 2026-11-10 (maintainer, /quest-plan on lite-07 rout
25. ✅ Asked how a relay safely forgets a publisher that is gone, after the model showed a per-neighbour echo is not enough once the origin sits behind a relay: **each route names the nodes it crossed, and a node never uses a route that names itself** ([moq-dev/moq#8487](https://github.com/moq-dev/moq/pull/8487), which holds the counterexamples and the model results). Feasibility still selects routes; the list is one per origin route, not the per-claim Hop ID list item 6 removed, and the echo and the drain rule stay as they are. As built: Babel's feasibility condition is unchanged, and a node never selects or certifies through such a route. Where the condition refuses it, it still counts as infeasible, so a relay whose neighbours all route through it holds its claims while one of them finds another way. Under a qualified key it counts only while its hops extend those of the route the node last sent under that key: a copy that a scoped peer hands back under a key derived from the node's own route never moves, so nothing waits on it. The origin names itself too, so a rotated identity's route is refused where it began, and a node names itself by a Hop ID that a rotation leaves alone. The hop limit is the wire's 32 and no lower. A change of hops or RTT alone lets go of no region, unless it changes whether the node may use the route: by crossing it, or by reaching the hop limit. This supersedes the claim, in the handoff contract and in decision 6 below, that the echo alone makes forgetting safe. First decided as a relay echoing a ROUTE_END only once its own downstream had; the model ran that the same day and it fails when a session closes before answering. Rejected: that deferred echo; never dropping the distance; a timer; relays as the only origin nodes.


26. ✅ Decided 2026-11-11 (maintainer, /quest-plan after [moq-dev/moq#8487](https://github.com/moq-dev/moq/pull/8487)'s reviews), asked whose copy of a publisher's claims a relay believes: **a route is shared per publisher and per scope, and a relay believes a route by that route's own path** ([the prototype](/quest/m2/cluster-routing/routes/stale-copies.md), [the model](/quest/m2/cluster-routing/routes/scope-model.md), then [the router](/quest/m2/cluster-routing/routes/scope.md)). A scope is the prefix a relay asked a neighbour for when its grant there is narrower than its interest. Today only a feasible neighbour counts, one strictly cheaper than the distance the relay remembers, so a relay's claims move whenever a cost or seqno does: it can forget a claim for good, a mesh with two grants never settles after one seqno advance, and behind a scoped neighbour it never shows what a farther one knows. Only a broadcast some relay carries gets its own route, and that route propagates ([cache-aware routing](/quest/m3/cache-routing/README.md) Plan item 8). Open, for the prototype to measure and the maintainer to pick: whether Babel's distance or the path alone, with a withdrawal that names the hop that died, keeps a route free of loops and stale copies. The contract's bullet on which neighbours certify stands until the model quest rewrites it. First decided the same day as any neighbour whose path to the publisher does not pass through the relay; tried on the router, two relays behind a scoped relay then keep a dead claim alive through each other, and the relay behind a scoped neighbour shows a claim it has no route to request. Rejected: that rule; believing a neighbour that is cheaper than the relay is now, which fixed the storm and the forgotten claim with no wire change but rests belief on distance; a path per broadcast as lite-06 has; link-state among relays; routes to relays.
26. ✅ Decided 2026-11-11 (maintainer, /quest-plan after [moq-dev/moq#8487](https://github.com/moq-dev/moq/pull/8487)'s reviews), asked whose copy of a publisher's claims a relay believes: **a route is shared per publisher and per scope, and a relay believes a route by that route's own path** ([the prototype](/quest/m1/route-stale-copies.md), [the model](/quest/m2/cluster-routing/routes/scope-model.md), then [the router](/quest/m2/cluster-routing/routes/scope.md)). A scope is the prefix a relay asked a neighbour for when its grant there is narrower than its interest. Today only a feasible neighbour counts, one strictly cheaper than the distance the relay remembers, so a relay's claims move whenever a cost or seqno does: it can forget a claim for good, a mesh with two grants never settles after one seqno advance, and behind a scoped neighbour it never shows what a farther one knows. Only a broadcast some relay carries gets its own route, and that route propagates ([cache-aware routing](/quest/m3/cache-routing/README.md) Plan item 8). Open, for the prototype to measure and the maintainer to pick: whether Babel's distance or the path alone, with a withdrawal that names the hop that died, keeps a route free of loops and stale copies. The contract's bullet on which neighbours certify stands until the model quest rewrites it. First decided the same day as any neighbour whose path to the publisher does not pass through the relay; tried on the router, two relays behind a scoped relay then keep a dead claim alive through each other, and the relay behind a scoped neighbour shows a claim it has no route to request. Rejected: that rule; believing a neighbour that is cheaper than the relay is now, which fixed the storm and the forgotten claim with no wire change but rests belief on distance; a path per broadcast as lite-06 has; link-state among relays; routes to relays.

The route layer's core landed in
[moq-dev/moq#7676](https://github.com/moq-dev/moq/pull/7676): a
Expand Down
12 changes: 7 additions & 5 deletions quest/m2/cluster-routing/routes/scope-model.md
Original file line number Diff line number Diff line change
Expand Up @@ -8,8 +8,10 @@ the prefix it covers, carries its own path, and is believed by a relay it did
not cross. TLC shows on it:

- A relay shows a claim exactly while it holds a route that covers the claim
and did not cross the relay, and the newest revision the relay knows still
has the claim. It shows the claim as it is at that revision.
and did not cross the relay, and the newest revision any covering route gave
it still has the claim. It shows the claim as it is at that revision. A
newer revision from a route that does not cover the claim says nothing
about it.
- Once nothing is in flight, no relay shows a claim that no path from its
publisher carries.
- A change of path or seqno alone starts, ends, and changes no claim a reader
Expand All @@ -20,7 +22,7 @@ not cross. TLC shows on it:
offers.

The model uses the rule
[the prototype](/quest/m2/cluster-routing/routes/stale-copies.md) picked for
[the prototype](/quest/m1/route-stale-copies.md) picked for
keeping a route free of stale copies. The rule this settles is written into
the epic's contract for
[the router](/quest/m2/cluster-routing/routes/scope.md) to implement. The
Expand All @@ -29,7 +31,7 @@ router's behaviour, the wire, and the draft do not change here.
## Plan

Decided 2026-11-11 (maintainer, /quest-plan). The decisions and what was
tried are in [the prototype](/quest/m2/cluster-routing/routes/stale-copies.md)'s
tried are in [the prototype](/quest/m1/route-stale-copies.md)'s
Plan and the [epic](/quest/m2/cluster-routing/routes/README.md)'s Plan item
26.

Expand Down Expand Up @@ -92,7 +94,7 @@ Public API: none. Wire: none.

## Required

- [A prototype settles what keeps a route free of stale copies](/quest/m2/cluster-routing/routes/stale-copies.md) - the rule for loops and stale copies that this model is written on
- [A prototype settles what keeps a route free of stale copies](/quest/m1/route-stale-copies.md) - the rule for loops and stale copies that this model is written on

## Related

Expand Down
6 changes: 3 additions & 3 deletions quest/m2/cluster-routing/routes/scope.md
Original file line number Diff line number Diff line change
Expand Up @@ -5,12 +5,12 @@
`route::Router` keys a route by its publisher and the prefix it covers, and
believes a route that did not cross it, as
[the model](/quest/m2/cluster-routing/routes/scope-model.md) settled. A relay
shows a claim exactly while such a route covers it and the newest revision
the relay knows still has the claim, two relays never keep a
shows a claim exactly while such a route covers it and the newest revision a
covering route gave it still has the claim, two relays never keep a
dead route alive through each other, a change of path or seqno alone changes
no claim a reader sees, and a relay behind a scoped neighbour reaches what a
farther one offers. The `residual_` tests
[the prototype](/quest/m2/cluster-routing/routes/stale-copies.md) pinned pass
[the prototype](/quest/m1/route-stale-copies.md) pinned pass
as plain tests, a sweep over meshes with scoped relays holds the rules at
every quiet point, and the draft and the epic's contract say what the router
does.
Expand Down
2 changes: 1 addition & 1 deletion quest/m3/cache-routing/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -87,7 +87,7 @@ Decided 2026-11-08 (maintainer, /quest-plan):
join a copy at a neighbour that is no closer to the publisher: the join
the Goal wants, and why item 2 stopped at one hop. What keeps a warm route
free of loops and stale copies is
[the prototype](/quest/m2/cluster-routing/routes/stale-copies.md)'s to
[the prototype](/quest/m1/route-stale-copies.md)'s to
measure, and the proof then holds that rule. Items 1 and 3 stand.
[moq-dev/moq#8457](https://github.com/moq-dev/moq/pull/8457) proves items
2 and 4 as first decided.
Expand Down
2 changes: 1 addition & 1 deletion quest/m3/route-keep-next-hop.md
Original file line number Diff line number Diff line change
Expand Up @@ -39,7 +39,7 @@ selection.
down-only route still moves to an equal one it may export, and test that.
- Check that every router test that names the next hop it expects still
means what it says, rather than editing expectations to match.
- [The prototype](/quest/m2/cluster-routing/routes/stale-copies.md) may
- [The prototype](/quest/m1/route-stale-copies.md) may
replace how a route is selected. If it has, apply this to the rule that
stands.
- Measure with `Sim`'s `hop_updates` count and, if it has landed,
Expand Down