Skip to content

Commit 9fc8837

Browse files
committed
Add minimum interval between reconnects
Protects against clients that disconnect right after connection, since the backoff retry won't come into play.
1 parent bde5101 commit 9fc8837

File tree

3 files changed

+14
-1
lines changed

3 files changed

+14
-1
lines changed

README.md

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -103,6 +103,8 @@ wsOpts = {
103103
awareness: new awarenessProtocol.Awareness(ydoc),
104104
// Specify the maximum amount to wait between reconnects (we use exponential backoff).
105105
maxBackoffTime: 2500
106+
// Specify the minimum amount to wait between reconnects if the previous connection succeeded but got closed right after.
107+
minRetryInterval: 2500
106108
}
107109
```
108110

package.json

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
{
22
"name": "y-websocket",
3-
"version": "3.0.0",
3+
"version": "3.1.0",
44
"description": "Websockets provider for Yjs",
55
"main": "./dist/y-websocket.cjs",
66
"module": "./src/y-websocket.js",

src/y-websocket.js

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -172,6 +172,12 @@ const closeWebsocketConnection = (provider, ws, event) => {
172172
* @param {WebsocketProvider} provider
173173
*/
174174
const setupWS = (provider) => {
175+
const timeout = provider.lastConnectAt ? Date.now() - provider.lastConnectAt.getTime() : provider.minRetryInterval
176+
if (timeout < provider.minRetryInterval && provider.wsUnsuccessfulReconnects === 0) {
177+
setTimeout(setupWS, timeout, provider)
178+
return
179+
}
180+
175181
if (provider.shouldConnect && provider.ws === null) {
176182
const websocket = new provider._WS(provider.url, provider.protocols)
177183
websocket.binaryType = 'arraybuffer'
@@ -194,6 +200,7 @@ const setupWS = (provider) => {
194200
closeWebsocketConnection(provider, websocket, event)
195201
}
196202
websocket.onopen = () => {
203+
provider.lastConnectAt = new Date()
197204
provider.wsLastMessageReceived = time.getUnixTime()
198205
provider.wsconnecting = false
199206
provider.wsconnected = true
@@ -265,6 +272,7 @@ export class WebsocketProvider extends ObservableV2 {
265272
* @param {typeof WebSocket} [opts.WebSocketPolyfill] Optionall provide a WebSocket polyfill
266273
* @param {number} [opts.resyncInterval] Request server state every `resyncInterval` milliseconds
267274
* @param {number} [opts.maxBackoffTime] Maximum amount of time to wait before trying to reconnect (we try to reconnect using exponential backoff)
275+
* @param {number} [opts.minRetryInterval] Minimum mount of time to wait between reconnects if the previous connection succeeded but got closed right after.
268276
* @param {boolean} [opts.disableBc] Disable cross-tab BroadcastChannel communication
269277
*/
270278
constructor (serverUrl, roomname, doc, {
@@ -275,6 +283,7 @@ export class WebsocketProvider extends ObservableV2 {
275283
WebSocketPolyfill = WebSocket,
276284
resyncInterval = -1,
277285
maxBackoffTime = 2500,
286+
minRetryInterval = 2500,
278287
disableBc = false
279288
} = {}) {
280289
super()
@@ -285,6 +294,7 @@ export class WebsocketProvider extends ObservableV2 {
285294
this.serverUrl = serverUrl
286295
this.bcChannel = serverUrl + '/' + roomname
287296
this.maxBackoffTime = maxBackoffTime
297+
this.minRetryInterval = minRetryInterval
288298
/**
289299
* The specified url parameters. This can be safely updated. The changed parameters will be used
290300
* when a new connection is established.
@@ -301,6 +311,7 @@ export class WebsocketProvider extends ObservableV2 {
301311
this.bcconnected = false
302312
this.disableBc = disableBc
303313
this.wsUnsuccessfulReconnects = 0
314+
this.lastConnectAt = null
304315
this.messageHandlers = messageHandlers.slice()
305316
/**
306317
* @type {boolean}

0 commit comments

Comments
 (0)