Repository navigation
fix(net): a relay resuming mid-group asks upstream for the group's head - #4829
Conversation
A relay whose upstream SUBSCRIBE starts mid-group (every takeover after a route change resumes there) held a copy without the group's first frames. A later reader that needed frame 0 was spliced from that copy, lagged, and parked until the group ended. A hang catalog or a compressed stats track is one long-lived group, so new viewers got no catalog and dashboards no stats, sometimes for minutes, on any edge downstream of a relay restart. No SUBSCRIBE_OK on this line reports the largest position, so ask from the head of the group instead; the requester's own start still skips the frames below it. This is the lite-06 half of #4741's widening on main. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
kixelated
left a comment
There was a problem hiding this comment.
Automated review by review (OpenAI)
Reviewed commit: 946c67a
No actionable introduced bugs found in the full two-file diff and relevant subscription, publisher, and splice code. Direction looks appropriate for a narrow release backport: rs/moq-net/src/lite/subscriber.rs:3233–3242 widens only the upstream start before the version gate, while preserving lite-06+ end precision and downstream frame positioning. This avoids importing the broader splicing changes; the small bandwidth trade-off is preferable to adding another recovery path here.
The open-group regression and controls are useful. One optional test strengthening: at rs/moq-net/tests/catalog_resume_snapshot.rs:83–85, assert the peer read result instead of discarding it, so the peer-read variant proves that step succeeded.
Verification: static review only; I did not run tests or independently verify the reported suite/check results.
|
Automated review of head It's a small, targeted fix that matches #4741's widening on Non-blocking
CI (Check, Test, and the platform builds) was still pending at review time. Verdict: MERGE. Nothing blocks, but consider item 1 before rolling this out to a mixed-version fleet. This is an automated review, not the maintainer's decision |
… own read Moves the head widening into the frame-bounds branch so older peers keep their existing rounding and debug log, and asserts the resumed peer reads its group from the snapshot (it lagged on lite-06/07 before the fix). Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
|
Addressed in a152fe5:
(Written by Claude Opus 5.5) |
|
Automated follow-up review of head The push moves the head widening inside the Earlier findings
Non-blocking
CI (Check, Test, and the platform builds) was still pending at review time. Verdict: MERGE. The earlier items are addressed, and what's left is test coverage and wording. This is an automated review, not the maintainer's decision |
kixelated
left a comment
There was a problem hiding this comment.
Automated review by review (OpenAI)
Reviewed commit: a152fe5; incremental review against 946c67a (one commit ahead, unchanged release base).
No new actionable bugs found. The assertion at rs/moq-net/tests/catalog_resume_snapshot.rs:84–88 addresses my earlier suggestion: timeouts, errors, and an incorrect first payload now fail. Expecting snapshot is consistent with the local spliced reader starting at frame 0 (src/model/resume.rs:1874–1881). Moving the widening into has_frame_bounds() at rs/moq-net/src/lite/subscriber.rs:3234–3241 preserves older-peer rounding and its debug logging. The direction remains a suitably small backport; no extra recovery machinery is needed for this delta.
I independently confirm the existing follow-up's coverage caveat: the upgraded peer widens its request before the relay sees it, so this integration test does not exercise a raw mid-group downstream request. The unit test covers widening itself. The previously reported mixed-version headless-upstream stall is documented, not fixed; keep that rollout limitation visible.
Verification: static delta/context review only. I did not run tests or verify CI results.
A peer running the fix widens its own start, so the relay's widening was never exercised. A local subscriber resuming at (G, 1) on the relay stands in for a not-yet-upgraded downstream peer; it lags on lite-06/07 without the fix. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
|
Addressed the follow-up in 606bd04:
(Written by Claude Opus 5.5) |
|
Automated follow-up review of head The push adds a Earlier findings
New issuesNone. The CI (Check, Test, and the platform builds) was still queued or running at review time. Verdict: MERGE. Everything from the earlier reviews is addressed. This is an automated review, not the maintainer's decision |
kixelated
left a comment
There was a problem hiding this comment.
Automated review by review (OpenAI)
Reviewed commit: 606bd04, against a152fe5 (one commit ahead; release base unchanged).
No new actionable bugs found. The Resume::Local setup at rs/moq-net/tests/catalog_resume_snapshot.rs:57–74 registers frame-precise demand directly on the relay and waits for its group before adding the fresh reader. This exercises the relay's upstream widening without the peer widening first, addressing the previous coverage gap. I independently agree with the existing follow-up assessment; it bypasses wire decoding but covers the relevant subscriber-side path. The original four scenarios remain represented, and the revised downstream-session wording is accurate.
Direction: the small test enum is a reasonable way to add this coverage without a raw-protocol harness or production-code complexity. The documented mixed-version headless-upstream limitation remains unchanged.
Verification: static delta/context review only; I did not run tests or independently verify the reported regression runs or CI.
|
Merge summary
(Written by Claude Opus 5.5) |
Conflicts: - rs/moq-net/src/lite/subscriber.rs: keep main. #4829's head widening is release's backport of #4741's widen_frame_bounds, which main already has. - rs/moq-net/tests/catalog_resume_snapshot.rs: left off main. Its lite-07 peer-fetch variant fails on main (quest/m1/lite07-head-fetch-arrival.md, #4830); that quest lands the test with its fix. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Problem
A relay whose upstream SUBSCRIBE starts mid-group holds a copy without that group's head. Every takeover after a route change resumes mid-group, which is how such a copy arises. A later reader that needs frame 0 is spliced from that copy.
poll_copyonly peeks the cache,start_at(0)clamps up, and the group diesLagged(no route can serve the rest of this group group=N frame=0 err=lagged). The reader then waits for a next group.A hang catalog and a compressed
.zstats track are each one long-lived open group. On moq.pro's staging fleet, after a relay restart, new viewers through the restarted edge and its downstream neighbor got no catalog, and the dashboard's stats stalled for minutes. Video escapes because its groups end every ~2 s.Approach
No SUBSCRIBE_OK on this line reports the largest position, so
widen_frame_boundsnow asks upstream from the head of the start group. The requester's own start still skips the frames below it. This is the lite-06 half of #4741's widening onmain(TrackServe::widen_frame_bounds, ungated there byhas_largest);releasehas no version that carries Largest.Impact
.zstats group, it is every delta since the group opened, which a fresh reader needs anyway.frame_bounds_survive_on_a_lite06_peerbecomesframe_bounds_start_at_the_group_head_on_a_lite06_peer. The end stays frame-precise; pre-lite-06 rounding is unchanged.Verification
tests/catalog_resume_snapshot.rs: a publisher holds an open group; a fresh relay pulls it; a mesh peer resumes at (G, 1); then a fresh reader on the relay must get G's snapshot. A variant also has the peer read its own copy from the head; before the fix, that read lagged on lite-06/07 too. It runs over lite-05, lite-06, lite-07-wip, and transport-17/22, with controls for no resume and for a resume at (G, 0).group 0 errored: lagged.just check.Alternatives
release: too broad for a backport. It is semver-breaking, a path becomes one broadcast (publishers restarting at group 0 need epoch names), and it changes splicing semantics across a mixed-version mesh.Follow-ups
mainkeeps main'ssubscriber.rs, since fix(net)!: resume route changes by reading the routes' copies; a path is one broadcast #4741 already covers this. The same test onmainexposes a separate lite-07 stall; it gets a quest.(Written by Claude Opus 5.5)
🤖 Generated with Claude Code