@rigxyz/tapd 0.6.10 → 0.6.11

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -2069,6 +2069,7 @@ function subscribe(opts) {
2069
2069
  };
2070
2070
  const scheduleReconnect = () => {
2071
2071
  if (stopped) return;
2072
+ opts.onDisconnected?.();
2072
2073
  const delay = backoff(attempt++);
2073
2074
  reconnectTimer = setTimeout(() => {
2074
2075
  reconnectTimer = null;
@@ -2098,6 +2099,8 @@ function asError(err, fallbackName) {
2098
2099
 
2099
2100
  // src/subscription.ts
2100
2101
  var DEFAULT_POLL_SECONDS = 3;
2102
+ var DEFAULT_HEALTHY_POLL_SECONDS = 60;
2103
+ var QUIET_AFTER_MS = 10 * 6e4;
2101
2104
  var SSE_APPLY_DEBOUNCE_MS = 50;
2102
2105
  async function startSubscription(opts) {
2103
2106
  const { mode } = opts;
@@ -2109,7 +2112,15 @@ async function startSubscription(opts) {
2109
2112
  fetch: opts.fetch
2110
2113
  });
2111
2114
  const pollSeconds = opts.pollSeconds ?? DEFAULT_POLL_SECONDS;
2115
+ const healthyPollSeconds = opts.healthyPollSeconds ?? DEFAULT_HEALTHY_POLL_SECONDS;
2112
2116
  let stopped = false;
2117
+ let sseHealthy = false;
2118
+ let lastRemoteChangeAt = Date.now();
2119
+ const nextPollMs = () => {
2120
+ const seconds = sseHealthy ? healthyPollSeconds : pollSeconds;
2121
+ const quiet = Date.now() - lastRemoteChangeAt >= QUIET_AFTER_MS;
2122
+ return seconds * 1e3 * (quiet ? 2 : 1);
2123
+ };
2113
2124
  let pollTimer;
2114
2125
  let sseApplyTimer;
2115
2126
  let sseSubscriber;
@@ -2135,6 +2146,7 @@ async function startSubscription(opts) {
2135
2146
  lastApplyResult = await withLock(
2136
2147
  () => applyOnce({ rootDir: opts.rootDir, client, stateDb, mode })
2137
2148
  );
2149
+ if (lastApplyResult.events.length > 0) lastRemoteChangeAt = Date.now();
2138
2150
  } catch (err) {
2139
2151
  if (isBindingDeletedError(err)) {
2140
2152
  const { deletedAt, deletedBy } = err.body;
@@ -2164,8 +2176,14 @@ async function startSubscription(opts) {
2164
2176
  const schedulePoll = () => {
2165
2177
  if (stopped) return;
2166
2178
  pollTimer = setTimeout(() => {
2179
+ pollTimer = void 0;
2167
2180
  triggerApply().finally(() => schedulePoll());
2168
- }, pollSeconds * 1e3);
2181
+ }, nextPollMs());
2182
+ };
2183
+ const reschedulePoll = () => {
2184
+ if (!pollTimer) return;
2185
+ clearTimeout(pollTimer);
2186
+ schedulePoll();
2169
2187
  };
2170
2188
  const scheduleSseApply = () => {
2171
2189
  if (stopped) return;
@@ -2183,8 +2201,19 @@ async function startSubscription(opts) {
2183
2201
  fetch: opts.fetch,
2184
2202
  heartbeatTimeoutMs: opts.sseHeartbeatTimeoutMs,
2185
2203
  onChange: () => scheduleSseApply(),
2204
+ // (Re)subscribed: catch up on anything sent while the stream was down.
2205
+ onSubscribed: () => {
2206
+ sseHealthy = true;
2207
+ scheduleSseApply();
2208
+ },
2186
2209
  onError: (err) => {
2187
2210
  console.error("tapd sse:", err.message);
2211
+ },
2212
+ // Failed or ended, a clean end included (a relay restart closes it).
2213
+ onDisconnected: () => {
2214
+ if (!sseHealthy) return;
2215
+ sseHealthy = false;
2216
+ reschedulePoll();
2188
2217
  }
2189
2218
  });
2190
2219
  }
@@ -3111,4 +3140,4 @@ export {
3111
3140
  scanAndPush,
3112
3141
  start
3113
3142
  };
3114
- //# sourceMappingURL=chunk-Q3PIHOTA.js.map
3143
+ //# sourceMappingURL=chunk-25SEJXF5.js.map