Skip to content

Reconnection

The ConvergeDB SDK automatically reconnects on disconnection. This page explains what happens to subscriptions during a disconnection and how to choose the right reconnection strategy.

The ConnectionManager handles TCP reconnection with exponential backoff:

  1. Connection loss is detected (socket close or liveness timeout).
  2. The SDK transitions to Reconnecting state.
  3. Reconnection attempts begin with a 100ms delay, doubling on each failure up to the configured maximum (ReconnectMaxDelayMs, default: 10 seconds).
  4. On successful reconnection, the SDK re-subscribes all active subscriptions.

No application code is needed for reconnection itself. The question is what happens to your subscription state.

When you subscribe, you choose a ReconnectBootstrapMode that controls what happens after reconnection:

await foreach (var change in players.SubscribeAsync(
bootstrap: true,
reconnectMode: ReconnectBootstrapMode.LiveOnly,
ct: ct))
{
// ...
}

On reconnection, the subscription resumes with live notifications only (no bootstrap). Any changes that occurred during the disconnection are lost. The subscriber’s local state may drift from the server’s state.

Use LiveOnly when:

  • The subscriber is an ephemeral UI or dashboard that will refresh naturally.
  • Missing a few updates during a brief disconnect is acceptable.
  • You want the fastest reconnection without the cost of a full re-scan.
await foreach (var change in players.SubscribeAsync(
bootstrap: true,
reconnectMode: ReconnectBootstrapMode.Full,
ct: ct))
{
// ...
}

On reconnection, the subscription re-subscribes with bootstrap: true. The server sends a complete entity snapshot followed by live notifications, just like the initial subscribe. This guarantees the subscriber’s local state matches the server exactly after reconnection.

Use Full when:

  • The subscriber maintains a mirror database or persistent cache that must stay in sync.
  • Missing updates is not acceptable (for example, analytics pipelines or replication targets).
  • You need a zero-drift guarantee.

The BootstrapState enum tracks the bootstrap status through the full lifecycle, including reconnections:

NotRequested → InProgress → Complete
Complete → RebootstrapInProgress → RebootstrapComplete

The Rebootstrap states let your application distinguish between the initial bootstrap and a reconnection re-bootstrap. This is important for mirror databases that need to switch between “full replace” and “incremental” modes.

var sub = await players.SubscribeAsync(
bootstrap: true,
reconnectMode: ReconnectBootstrapMode.Full,
ct: ct);
sub.BootstrapStatusChanged += status =>
{
switch (status)
{
case BootstrapState.InProgress:
case BootstrapState.RebootstrapInProgress:
// Server is scanning. Expect Bootstrap notifications.
// Mirror databases should prepare for a full-replace cycle.
break;
case BootstrapState.Complete:
case BootstrapState.RebootstrapComplete:
// Scan complete. Local state is now fully caught up.
// Mirror databases can commit the full-replace batch.
break;
}
};
await foreach (var change in sub.ReadAllAsync(ct))
{
ApplyChange(state, change);
}

You can trigger a re-bootstrap on demand without waiting for a disconnection:

await sub.RebootstrapAsync();

This sends an UNSUBSCRIBE followed by a SUBSCRIBE with bootstrap: true. The BootstrapState transitions to RebootstrapInProgress and then RebootstrapComplete.

Use this for periodic reconciliation: subscribe once with ReconnectBootstrapMode.Full, then call RebootstrapAsync() on a timer to periodically verify local state consistency.

Here is the complete sequence of events during a disconnection and reconnection with ReconnectBootstrapMode.Full:

  1. Connection lost. The SDK transitions to Reconnecting state. Notifications stop arriving.
  2. Reconnection. After exponential backoff, a new TCP connection is established. The SDK sends CONNECT with the original SourceId.
  3. Re-subscription. The SDK iterates all active subscriptions. For subscriptions with Full mode, it sends SUBSCRIBE with bootstrap: true.
  4. BOOTSTRAP_BEGIN. The server begins scanning. BootstrapState transitions to RebootstrapInProgress. The BootstrapStatusChanged event fires.
  5. Bootstrap + live notifications. Bootstrap and live notifications arrive interleaved on the subscription channel. Process them all with version-wins merge.
  6. BOOTSTRAP_END. BootstrapState transitions to RebootstrapComplete. The BootstrapStatusChanged event fires. Local state is fully caught up.
  7. Live resumes. Only Created, Updated, and Deleted notifications arrive from this point.