react-realtime-hooks 1.4.2 → 2.0.0
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.
- package/README.md +10 -4
- package/dist/index.cjs +11 -6
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.cts +11 -1
- package/dist/index.d.ts +11 -1
- package/dist/index.js +11 -6
- package/dist/index.js.map +1 -1
- package/package.json +4 -2
package/README.md
CHANGED
|
@@ -88,7 +88,6 @@ export function NotificationsPanel() {
|
|
|
88
88
|
parseMessage: (event) => JSON.parse(String(event.data)) as IncomingMessage,
|
|
89
89
|
reconnect: {
|
|
90
90
|
initialDelayMs: 1_000,
|
|
91
|
-
maxAttempts: null,
|
|
92
91
|
},
|
|
93
92
|
heartbeat: {
|
|
94
93
|
intervalMs: 10_000,
|
|
@@ -239,7 +238,6 @@ export function ChatSocket() {
|
|
|
239
238
|
parseMessage: (event) => JSON.parse(String(event.data)) as IncomingMessage,
|
|
240
239
|
reconnect: {
|
|
241
240
|
initialDelayMs: 1_000,
|
|
242
|
-
maxAttempts: null,
|
|
243
241
|
},
|
|
244
242
|
heartbeat: {
|
|
245
243
|
intervalMs: 10_000,
|
|
@@ -393,6 +391,8 @@ export function GatedNotifications() {
|
|
|
393
391
|
initialDelayMs: 1_000,
|
|
394
392
|
maxAttempts: null,
|
|
395
393
|
},
|
|
394
|
+
// ^ pass `null` explicitly to opt back into unlimited reconnect attempts;
|
|
395
|
+
// the default in 2.0 caps retries at 10.
|
|
396
396
|
url: "ws://localhost:8080/notifications",
|
|
397
397
|
});
|
|
398
398
|
|
|
@@ -508,7 +508,7 @@ retry loop.
|
|
|
508
508
|
| `maxDelayMs` | `number` | `30000` | Delay cap |
|
|
509
509
|
| `backoffFactor` | `number` | `2` | Exponential multiplier |
|
|
510
510
|
| `jitterRatio` | `number` | `0.2` | Randomized variance ratio |
|
|
511
|
-
| `maxAttempts` | `number \| null` | `
|
|
511
|
+
| `maxAttempts` | `number \| null` | `10` | Max attempts before `"stopped"`; pass `null` for unlimited |
|
|
512
512
|
| `getDelayMs` | `ReconnectDelayStrategy` | `undefined` | Custom delay strategy |
|
|
513
513
|
| `resetOnSuccess` | `boolean` | `true` | Resets attempt count after success |
|
|
514
514
|
| `onSchedule` | `(attempt) => void` | `undefined` | Called when an attempt is scheduled |
|
|
@@ -540,7 +540,7 @@ retry loop.
|
|
|
540
540
|
| -------------- | --------------------------------------------------- | ----------- | ------------------------------------------- |
|
|
541
541
|
| `enabled` | `boolean` | `true` | Enables the heartbeat loop |
|
|
542
542
|
| `intervalMs` | `number` | Required | Beat interval |
|
|
543
|
-
| `timeoutMs` | `number`
|
|
543
|
+
| `timeoutMs` | `number \| null` | `10_000` | Timeout in ms before `hasTimedOut` becomes `true`; pass `null` to disable |
|
|
544
544
|
| `message` | `TOutgoing \| (() => TOutgoing)` | `undefined` | Optional heartbeat payload |
|
|
545
545
|
| `beat` | `() => void \| boolean \| Promise<void \| boolean>` | `undefined` | Custom beat side effect |
|
|
546
546
|
| `matchesAck` | `(message) => boolean` | `undefined` | Ack matcher |
|
|
@@ -694,6 +694,12 @@ Run the local playground:
|
|
|
694
694
|
npm run demo
|
|
695
695
|
```
|
|
696
696
|
|
|
697
|
+
## Migrating from 1.x
|
|
698
|
+
|
|
699
|
+
Two defaults change in 2.0 (`reconnect.maxAttempts` → `10`,
|
|
700
|
+
`heartbeat.timeoutMs` → `10_000`). See [MIGRATING.md](./MIGRATING.md) for the
|
|
701
|
+
exact diff and how to restore 1.x behaviour.
|
|
702
|
+
|
|
697
703
|
## Contributing
|
|
698
704
|
|
|
699
705
|
Development and release workflow live in [CONTRIBUTING.md](./CONTRIBUTING.md).
|
package/dist/index.cjs
CHANGED
|
@@ -315,6 +315,7 @@ var DEFAULT_RECONNECT_OPTIONS = {
|
|
|
315
315
|
enabled: true,
|
|
316
316
|
initialDelayMs: 1e3,
|
|
317
317
|
jitterRatio: 0.2,
|
|
318
|
+
maxAttempts: 10,
|
|
318
319
|
maxDelayMs: 3e4,
|
|
319
320
|
resetOnSuccess: true
|
|
320
321
|
};
|
|
@@ -366,7 +367,7 @@ var normalizeReconnectOptions = (options) => {
|
|
|
366
367
|
jitterRatio: sanitizeJitterRatio(
|
|
367
368
|
options?.jitterRatio ?? DEFAULT_RECONNECT_OPTIONS.jitterRatio
|
|
368
369
|
),
|
|
369
|
-
maxAttempts: sanitizeMaxAttempts(options
|
|
370
|
+
maxAttempts: options?.maxAttempts === void 0 ? DEFAULT_RECONNECT_OPTIONS.maxAttempts : sanitizeMaxAttempts(options.maxAttempts),
|
|
370
371
|
maxDelayMs,
|
|
371
372
|
resetOnSuccess: options?.resetOnSuccess ?? DEFAULT_RECONNECT_OPTIONS.resetOnSuccess
|
|
372
373
|
};
|
|
@@ -584,6 +585,7 @@ var useReconnect = (options = {}) => {
|
|
|
584
585
|
status: state.status
|
|
585
586
|
};
|
|
586
587
|
};
|
|
588
|
+
var DEFAULT_HEARTBEAT_TIMEOUT_MS = 1e4;
|
|
587
589
|
var createInitialState2 = (isRunning) => ({
|
|
588
590
|
hasTimedOut: false,
|
|
589
591
|
isRunning,
|
|
@@ -617,13 +619,14 @@ var useHeartbeat = (options) => {
|
|
|
617
619
|
options.onTimeout?.();
|
|
618
620
|
});
|
|
619
621
|
const scheduleTimeout = useStableCallback(() => {
|
|
620
|
-
|
|
622
|
+
const timeoutMs = options.timeoutMs === void 0 ? DEFAULT_HEARTBEAT_TIMEOUT_MS : options.timeoutMs;
|
|
623
|
+
if (timeoutMs === null) {
|
|
621
624
|
timeoutRef.current.cancel();
|
|
622
625
|
return;
|
|
623
626
|
}
|
|
624
627
|
timeoutRef.current.schedule(() => {
|
|
625
628
|
handleTimeout();
|
|
626
|
-
},
|
|
629
|
+
}, timeoutMs);
|
|
627
630
|
});
|
|
628
631
|
const handleBeatSuccess = useStableCallback((performedAt) => {
|
|
629
632
|
commitState((current) => ({
|
|
@@ -942,8 +945,9 @@ var useWebSocket = (options) => {
|
|
|
942
945
|
const nextSocketEpochRef = react.useRef(0);
|
|
943
946
|
const controller = useWebSocketController();
|
|
944
947
|
const [openNonce, setOpenNonce] = react.useState(0);
|
|
948
|
+
const initialStatus = !supported || resolvedUrl === null ? "closed" : connect ? "connecting" : "idle";
|
|
945
949
|
const [state, setState] = react.useState(
|
|
946
|
-
() => createInitialState4(
|
|
950
|
+
() => createInitialState4(initialStatus)
|
|
947
951
|
);
|
|
948
952
|
const stateRef = react.useRef(state);
|
|
949
953
|
react.useInsertionEffect(() => {
|
|
@@ -985,7 +989,7 @@ var useWebSocket = (options) => {
|
|
|
985
989
|
startOnMount: false
|
|
986
990
|
};
|
|
987
991
|
if (heartbeatConfig !== null && heartbeatConfig.timeoutMs !== void 0) {
|
|
988
|
-
heartbeatHookOptions.timeoutMs = heartbeatConfig.timeoutMs;
|
|
992
|
+
heartbeatHookOptions.timeoutMs = heartbeatConfig.timeoutMs ?? null;
|
|
989
993
|
}
|
|
990
994
|
if (heartbeatConfig !== null && heartbeatConfig.matchesAck !== void 0) {
|
|
991
995
|
heartbeatHookOptions.matchesAck = heartbeatConfig.matchesAck;
|
|
@@ -1517,8 +1521,9 @@ var useEventSource = (options) => {
|
|
|
1517
1521
|
const suppressReconnectRef = react.useRef(false);
|
|
1518
1522
|
const terminalErrorRef = react.useRef(null);
|
|
1519
1523
|
const [openNonce, setOpenNonce] = react.useState(0);
|
|
1524
|
+
const initialStatus = !supported || resolvedUrl === null ? "closed" : connect ? "connecting" : "idle";
|
|
1520
1525
|
const [state, setState] = react.useState(
|
|
1521
|
-
() => createInitialState5(
|
|
1526
|
+
() => createInitialState5(initialStatus)
|
|
1522
1527
|
);
|
|
1523
1528
|
const stateRef = react.useRef(state);
|
|
1524
1529
|
react.useInsertionEffect(() => {
|