Skip to content

Add automatic reconnection with exponential backoff#1246

Merged
kixelated merged 2 commits into
mainfrom
claude/add-rust-reconnect-support-HSOCD
Apr 9, 2026
Merged

Add automatic reconnection with exponential backoff#1246
kixelated merged 2 commits into
mainfrom
claude/add-rust-reconnect-support-HSOCD

Conversation

@kixelated

Copy link
Copy Markdown
Collaborator

Summary

This PR adds automatic reconnection functionality to the MOQ native client, allowing it to maintain persistent connections with exponential backoff retry logic.

Key Changes

  • New reconnect module: Implements Reconnect handle and Backoff configuration for managing automatic reconnection attempts

    • Backoff struct with configurable initial delay (default 1s), multiplier (default 2x), and maximum delay (default 30s)
    • Supports CLI arguments and environment variables for backoff configuration
    • Supports serialization/deserialization via serde
  • Reconnect handle: Spawns a background tokio task that:

    • Attempts to connect to a given URL
    • Waits for the session to close
    • Automatically reconnects with exponential backoff on failure
    • Can be stopped by dropping the handle or calling close()
  • Client integration:

    • Added backoff field to ClientConfig with CLI and serde support
    • Added backoff field to Client struct
    • New Client::reconnect() method to start the background reconnection loop
    • Backoff configuration is passed through from config to the reconnect task

Implementation Details

  • The reconnect loop resets the backoff delay to initial value on successful connection
  • Exponential backoff is capped at the configured maximum delay
  • Uses tokio::task::AbortHandle for clean task cancellation
  • Includes unit tests for backoff default values
  • Comprehensive logging at info/warn levels for connection state changes

https://claude.ai/code/session_01BTTwQv5UW7yFAuYiKBPM8X

…backoff

Add automatic reconnection support for MoQ clients. Reconnect spawns a
background tokio task that connects, waits for session close, then
reconnects with configurable exponential backoff (default: 1s/2x/30s).

Dropping the handle or calling close() aborts the background task.

https://claude.ai/code/session_01BTTwQv5UW7yFAuYiKBPM8X
@coderabbitai

coderabbitai Bot commented Apr 9, 2026

Copy link
Copy Markdown
Contributor

Warning

Rate limit exceeded

@kixelated has exceeded the limit for the number of commits that can be reviewed per hour. Please wait 1 minutes and 15 seconds before requesting another review.

Your organization is not enrolled in usage-based pricing. Contact your admin to enable usage-based pricing to continue reviews beyond the rate limit, or try again in 1 minutes and 15 seconds.

⌛ How to resolve this issue?

After the wait time has elapsed, a review can be triggered using the @coderabbitai review command as a PR comment. Alternatively, push new commits to this PR.

We recommend that you space out your commits to avoid hitting the rate limit.

🚦 How do rate limits work?

CodeRabbit enforces hourly rate limits for each developer per organization.

Our paid plans have higher rate limits than the trial, open-source and free plans. In all cases, we re-allow further reviews after a brief timeout.

Please see our FAQ for further information.

ℹ️ Review info
⚙️ Run configuration

Configuration used: Organization UI

Review profile: CHILL

Plan: Pro

Run ID: 75220528-f0d0-49d3-8882-17797b1eafc7

📥 Commits

Reviewing files that changed from the base of the PR and between b57b9f8 and ea68a48.

📒 Files selected for processing (7)
  • js/lite/src/connection/reload.ts
  • rs/hang/examples/subscribe.rs
  • rs/hang/examples/video.rs
  • rs/moq-boy/src/main.rs
  • rs/moq-cli/src/client.rs
  • rs/moq-clock/src/main.rs
  • rs/moq-native/src/reconnect.rs

Walkthrough

This change introduces configurable exponential-backoff reconnection functionality to the MOQ native client. A new reconnect module is created, exposing a Backoff struct that configures initial delay, multiplier, and maximum delay with CLI argument parsing and serde support. A Reconnect handle spawns a background task that attempts connections, logs status, and on failure sleeps using exponentially-backed-off delays before retrying. The Client stores a Backoff instance and exposes a reconnect() method that returns a Reconnect handle. The new module is re-exported through the library root.

🚥 Pre-merge checks | ✅ 3
✅ Passed checks (3 passed)
Check name Status Explanation
Title check ✅ Passed The title 'Add automatic reconnection with exponential backoff' directly and clearly describes the main feature being added to the codebase.
Description check ✅ Passed The description is comprehensive and closely related to the changeset, providing clear context about the new reconnect module, Backoff configuration, Reconnect handle, and Client integration.
Docstring Coverage ✅ Passed No functions found in the changed files to evaluate docstring coverage. Skipping docstring coverage check.

✏️ Tip: You can configure your own custom pre-merge checks in the settings.

✨ Finishing Touches
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Commit unit tests in branch claude/add-rust-reconnect-support-HSOCD
✨ Simplify code
  • Create PR with simplified code
  • Commit simplified code in branch claude/add-rust-reconnect-support-HSOCD

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands and usage tips.

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

🧹 Nitpick comments (1)
rs/moq-native/src/reconnect.rs (1)

70-83: Consider adding a delay or jitter after session close.

When a session closes (lines 74-75), reconnection happens immediately without any delay. If the server accepts connections but quickly terminates sessions (e.g., due to overload or misconfiguration), this could cause rapid reconnection attempts. Consider adding a small base delay or jitter after clean session closure.

♻️ Optional: Add minimal delay after session close
 				Ok(session) => {
 					tracing::info!(%url, "connected");
 					delay = backoff.initial;
 					let _ = session.closed().await;
 					tracing::warn!(%url, "session closed, reconnecting");
+					// Small delay before reconnecting to avoid hammering server
+					tokio::time::sleep(Duration::from_millis(100)).await;
 				}
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@rs/moq-native/src/reconnect.rs` around lines 70 - 83, The Ok branch for
client.connect handles clean session closure immediately restarting the loop
(involving session.closed()). After session.closed().await, introduce a short
sleep with jitter instead of immediate reconnect: compute a small base delay
(e.g., backoff.initial or a configured min_close_delay) add randomized jitter,
await tokio::time::sleep on that duration, and then reset delay =
backoff.initial as currently done; this change is localized to the Ok(session)
arm around session.closed() to prevent tight reconnect loops when the server is
closing sessions.
🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.

Nitpick comments:
In `@rs/moq-native/src/reconnect.rs`:
- Around line 70-83: The Ok branch for client.connect handles clean session
closure immediately restarting the loop (involving session.closed()). After
session.closed().await, introduce a short sleep with jitter instead of immediate
reconnect: compute a small base delay (e.g., backoff.initial or a configured
min_close_delay) add randomized jitter, await tokio::time::sleep on that
duration, and then reset delay = backoff.initial as currently done; this change
is localized to the Ok(session) arm around session.closed() to prevent tight
reconnect loops when the server is closing sessions.

ℹ️ Review info
⚙️ Run configuration

Configuration used: Organization UI

Review profile: CHILL

Plan: Pro

Run ID: b248db0b-bebc-4639-ab66-d49ac85d474f

📥 Commits

Reviewing files that changed from the base of the PR and between 55b28a5 and b57b9f8.

📒 Files selected for processing (3)
  • rs/moq-native/src/client.rs
  • rs/moq-native/src/lib.rs
  • rs/moq-native/src/reconnect.rs

- Add optional `timeout` to Backoff (resets after each successful
  connection, gives up with error when exceeded)
- Add `closed().await` to Reconnect (resolves on timeout or close)
- Migrate moq-cli, moq-clock, moq-boy, and hang examples to use
  `reconnect()` instead of `connect()`
- Add `timeout` and `closed` promise to JS Reload class

https://claude.ai/code/session_01BTTwQv5UW7yFAuYiKBPM8X
@kixelated kixelated merged commit a215709 into main Apr 9, 2026
1 of 2 checks passed
@kixelated kixelated deleted the claude/add-rust-reconnect-support-HSOCD branch April 9, 2026 16:29
This was referenced Apr 9, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants