sse-events
SSE event source polyfill wrapped in Node.js like EventEmitter with performance fixes and custom api. Compatible with React/React-Native.
Motivation
- Improved retry algorithm to avoid loops and memory leaks
- Automatic close of connection upon server error codes (4xx, 5xx, ...)
- EventEmitter api
- Singletron pattern
- Listeners persisting across retries and/or connection close events
- Dynamic change of headers, path and parameters
- Random retry interval to reduce server request concurrency
- Dynamic progressive fallback interval for long lasting connection retries
- React/React-Native compatible
Implementation based on:
Installing
Run the following command in your project's directory to grab the latest published version of this code:
$ npm install sse-events --save
or
$ yarn add sse-events
Using in your project
import EventSource from 'sse-events';
Create an instance, providing the configuration options (optional)
const sse = new EventSource({
url: SSE_BASE_URL,
path: '/some/path',
options: {
headers: {
'User-Agent': USER_AGENT,
Authorization: '...'
}
},
reconnectInterval: 500,
retryOnNetworkError: false
});
Bind few event listeners:
const { ON_ERROR, ON_OPEN } = EventSource.types;
sse.addEventListener('init', message => debug('SSE Init: ', message));
sse.addEventListener(ON_OPEN, () => {
sse.retrying = false;
});
sse.addEventListener(ON_ERROR, (error: ESError) => {
if (
error &&
!sse.retrying &&
error.data && error.data.code &&
(
(error.data.code >= 200 && error.data.code <= 202) ||
error.data.code === 204
)
) {
delete sse.options.headers.Authorization;
sse.retrying = true;
store.dispatch(refreshLogin())
.then(res => (res.data && sse.open()))
.catch(() => null);
return;
}
sse.retrying = false;
});
Now call the open
method to establish the connection. No matter how may times this method is called, just
one AND ONLY ONE connection is open a time. Some errors can interrupt the SSE retry algorithm and thus further call to this method is required to re-establish the connection. Listeners DON'T CLOSE if this method is called.
sse.open();
SSE connection can be suspended calling the close
method. Instance headers, params or other options don't apply to the on-going connection unless manually closed and open again.
sse.close();
To close the connection and remove all listeners call the destroy
method. Following calls to open
WILL NOT restore previous event listeners.
sse.destroy();
Headers params can be set/updated calling this method.
sse.setHeaders({
Authorization: '...'
});
Url params can be set/updated calling this method.
sse.setParams({
scope: 'all'
});
Connection url and path can be set/updated directly from instance properties.
sse.path = '/path/to/sse/resource';
sse.url = 'example.com'
Connection States
const {
CONNECTING = 0,
OPEN = 1,
CLOSED = 2
} = sse;
Event Types
const {
ON_OPEN = 'open',
ON_ERROR = 'error',
ON_CLOSE = 'close',
ON_STATE = 'state',
ON_TIMEOUT = 'timeout'
} = EventSource.types;
Configuration Options
sse.reconnectInterval || 1000;
sse.maxInterval || 15000;
sse.minInterval || 1000;
sse.maxAttempts || -1;
sse.retryOnNetworkError || true;
sse.retryOnServerError || false;
sse.serverErrorCodes || [502, 503, 504];
sse.url
sse.options
sse.params
sse.path
sse.readyState
License
This project is licensed under the MIT License