Détail du package

better-sse

MatthewWid29.3kMIT0.15.1

Dead simple, dependency-less, spec-compliant server-sent events implementation written in TypeScript.

server-sent-events, sse, realtime, real-time

readme

Better SSE

npm jsr MIT license Downloads GitHub stars

A dead simple, dependency-less, spec-compliant server-sent events implementation written in TypeScript.

This package aims to be the easiest to use, most compliant and most streamlined solution to server-sent events that is framework-agnostic and feature-rich.

Please consider starring the project on GitHub ⭐.

Why use Server-sent Events?

Server-sent events (SSE) is a standardised protocol that allows web-servers to push data to clients without the need for alternative mechanisms such as pinging, long-polling or WebSockets.

Using SSE can allow for significant savings in bandwidth and battery life on portable devices and will work with your existing infrastructure as it operates directly over the HTTP protocol without the need for the connection upgrade that WebSockets require.

Compared to WebSockets it has comparable performance and bandwidth usage, especially over HTTP/2, and natively includes event ID generation and automatic reconnection when clients are disconnected.

Read the Getting Started guide for more.

Highlights

  • Compatible with all popular HTTP frameworks (Express, Hono, Fastify, Nest, Next.js, Bun, Deno, etc.)
  • Fully written in TypeScript (+ ships with types directly).
  • Thoroughly tested (+ 100% code coverage!).
  • Comprehensively documented with guides and API documentation.
  • Channels allow you to broadcast events to many clients at once.
  • Event buffers allow you to batch events for increased performance and lower bandwidth usage.
  • Configurable reconnection time, message serialization and data sanitization (with good defaults).
  • Trust or ignore the client-given last event ID.
  • Automatically send keep-alive pings to keep connections open.
  • Add or override the response status code and headers.
  • Pipe streams and iterables directly from the server to the client as a series of events.
  • Support for popular EventSource polyfills event-source-polyfill and eventsource-polyfill.

See a comparison with other SSE libraries in the documentation.

Installation

Better SSE is published as a package on npm and the JSR. You can install it with any package manager:

npm install better-sse
yarn add better-sse
pnpm add better-sse
bun add better-sse
deno install jsr:@mwid/better-sse

Better SSE ships with types built in. No need to install from DefinitelyTyped for TypeScript users!

Usage

The examples below show usage with Express and Hono, but Better SSE works with any web-server framework that uses the Node HTTP module or the Fetch API.

See the Recipes section of the documentation for use with other frameworks and libraries.


Use sessions to push events to clients:

// Server - Express
import { createSession } from "better-sse"

app.get("/sse", async (req, res) => {
    const session = await createSession(req, res)
    session.push("Hello world!", "message")
})
// Server - Hono
import { createResponse } from "better-sse"

app.get("/sse", (c) =>
    createResponse(c.req.raw, (session) => {
        session.push("Hello world!", "message")
    })
)
// Client
const eventSource = new EventSource("/sse")

eventSource.addEventListener("message", ({ data })) => {
    const contents = JSON.parse(data)
    console.log(contents) // Hello world!
})

Use channels to send events to many clients at once:

import { createSession, createChannel } from "better-sse"

const channel = createChannel()

app.get("/sse", async (req, res) => {
    const session = await createSession(req, res)

    channel.register(session)

    channel.broadcast("A user has joined.", "join-notification")
})

Use batching to send multiple events at once for improved performance and lower bandwidth usage:

await session.batch(async (buffer) => {
    await buffer.iterate(["My", "huge", "event", "list"])
})

Loop over sync and async iterables and send each value as an event:

const iterable = [1, 2, 3]

await session.iterate(iterable)

Pipe readable stream data to the client as a stream of events:

const stream = Readable.from([1, 2, 3])

await session.stream(stream)

Check the API documentation and live examples for information on getting more fine-tuned control over your data such as managing event IDs, data serialization, event filtering, dispatch controls and more!

Documentation

API documentation, getting started guides and usage with other frameworks is available on the documentation website.

Contributing

This library is always open to contributions whether it be code, bug reports, documentation or anything else.

Please submit suggestions, bugs and issues to the GitHub issues page.

For code or documentation changes submit a pull request on GitHub.

Local Development

Install Node (with n):

curl -L https://git.io/n-install | bash
n auto

Install dependencies (with pnpm):

npm i -g pnpm
pnpm i

Run tests (with Vitest):

pnpm t

Lint and format (with Biome):

pnpm lint
pnpm format

Bundle for distribution (with tsup):

pnpm build

License

This project is licensed under the MIT license.

changelog

Changelog

All notable changes to this project will be documented in this file.

The format is based on Keep a Changelog, and this project adheres to Semantic Versioning.

Unreleased

Changed

Fixed

  • Fixed a warning being printed by the Node internals when adding more than ten listeners to events emitted by sessions and channels.

0.15.1 - 2025-05-26

Added

Fixed

  • Fixed the stream, iterate and EventBuffer#clear methods not having explicit return types, resulting in slow inference in certain environments.

0.15.0 - 2025-05-22

Added

  • Added support for the Session constructor to be able to take in a Request (and optionally a Response) object from the Fetch API.
  • Added the Session#getRequest and Session#getResponse methods to retrieve the Fetch API Request and Response objects, respectively.
  • Added the createResponse utility function to create a Session instance and immediately return its associated Response object.
  • Added type overloads for each combination of arguments to createSession and the Session constructor.
  • Added support for passing a ReadableStream from the Web Streams API to Session#stream and EventBuffer#stream.

Changed

  • Update type of Session constructor options#headers argument to accept any string->(string | string[] | undefined) type rather than only OutgoingHttpHeaders.
  • Update the Session constructor options#headers argument to omit headers whose values are given as undefined, rather than an empty string.
  • Update the Session constructor to throw if given an IncomingMessage or Http2ServerRequest with no corresponding ServerResponse or Http2ServerResponse, respectively.

Fixed

Removed

  • Removed the deprecated Session .event, .data, .id, .retry, .comment, .dispatch and .flush methods.

0.14.1 - 2024-10-27

Changed

0.14.0 - 2024-10-18

Fixed

  • Fixed default state type when creating sessions and channels with createSession and createChannel being set to unknown instead of DefaultSessionState and DefaultChannelState, respectively.
  • Fixed package directly exporting a single object containing exports, breaking named imports when using ESModules, and instead dual-export two separate builds to support both ESM and CJS.

Removed

  • Dropped support for Node 17 and below.

0.13.0 - 2024-08-23

Added

  • Added the ability to set an initial value for the state property in the Session and Channel constructor options objects.

Removed

  • Removed constraints that enforced that State generics passed to Session and Channel extend from Record<string, unknown>.

0.12.1 - 2024-05-24

Fixed

  • Fixed types for channel and session emitted event names.

0.12.0 - 2024-05-10

Added

0.11.0 - 2024-02-08

Added

  • Added the SseError custom error object that wraps all thrown errors.

Changed

  • Update the Session#push method to throw if the session is not connected.

Fixed

  • Fixed session not detecting a response stream disconnect.

0.10.0 - 2023-09-28

Added

  • Added the Session#batch method that can be used to batch multiple events into a single transmission over the wire.
  • Added the EventBuffer class that can be used to write raw spec-compliant SSE fields into a text buffer that can be sent directly over the wire.

Deprecated

  • Deprecate the Session .event, .data, .id, .retry, .comment, .dispatch and .flush methods in favour of using event buffers instead.

0.9.0 - 2023-08-14

Added

  • Added the ability to type the state property of sessions registered with a Channel via an optional second generic argument to the Channel constructor.
  • Added the DefaultChannelState interface that may be used via module augmentation to alter the default channel state type for all channels.

Changed

0.8.0 - 2022-06-02

Added

  • Added an internal data buffer to Session that buffers written data internally until it is flushed to the client using the new Session#flush method.
  • Added the Pragma, X-Accel-Buffering headers and add additional values to the Cache-Control default header to further disable all forms of caching.
  • Added support for supplying the Node HTTP/2 compatibility API Http2ServerRequest and Http2ServerResponse objects to the Session constructor req and res parameters, respectively.

Changed

  • Update the Session#event, Session#data, Session#id, Session#retry and Session#comment methods to write to the internal data buffer instead of sending the field data over the wire immediately.
  • Update the Session#dispatch method to only write a newline (and to the internal data buffer) and not flush the written data to the client.
  • Update the Channel#broadcast method to generate its own custom event ID and thus add it as an additional argument to its broadcast event callback function.
  • Update the Channel#register and Channel#deregister to not do anything if the channel is already registered or deregistered, respectively.
  • Update the Session constructor options header field to overwrite conflicting default headers instead of being ignored.
  • Update auto-generated event IDs to be guaranteed to be a cryptographically unique string instead of a pseudorandomly generated string of eight characters.

Fixed

  • Fixed the Channel session-disconnected being fired after instead of before the session is deregistered.

Removed

  • Removed the ability to pass null to Session#id. Give no arguments at all instead.

0.7.1 - 2022-01-11

Fixed

  • Removed type-declarations generated from unit testing files.

0.7.0 - 2022-01-08

Added

  • Added the ability to the Session#push method to set a custom event ID.
  • Added a new Session push event that is emitted with the event data, name and ID when the Session#push method is called.
  • Added the Channel#state property to have a safe namespace for keeping information attached to the channel.

Changed

  • Update the arguments for the Session#push and Channel#broadcast methods and their corresponding emitted event callbacks to always have the event data first and event name as an optional argument second.
  • Update the Channel#broadcast method options TypeScript typings to explicitly mandate a boolean return-type instead of allowing any truthy or falsy value.
  • Update the Channel#broadcast method event name argument to be optional and default to "message" if not given.
  • Update the Session#state generic argument to default to a new SessionState interface that can be augmented via declaration merging to override the session state type for all session objects without explicitly providing a generic argument to each reference to Session.
  • Rename the Session and Channel Events interfaces to SessionEvents and ChannelEvents respectively and export them publicly allowing the user to properly type non-inlined event handler callback functions.

0.6.0 - 2021-10-28

Added

  • Added the Session#iterate method that allows processing iterables and sending yielded values to the client as events.
  • Added types for Session and Channel event listener callback function arguments.
  • Added the ability to type Session#state using an optional generic argument for createSession and the Session constructor.

Changed

0.5.0 - 2021-07-17

Added

Fixed

0.4.0 - 2021-07-09

Added

Fixed

  • Fixed an issue where installing the package using npm would throw an error mandating it be installed with pnpm.