first commit
This commit is contained in:
57
docs/api-stack/api/api-ws-bun/src/reconnect/event-buffer.md
Normal file
57
docs/api-stack/api/api-ws-bun/src/reconnect/event-buffer.md
Normal file
@@ -0,0 +1,57 @@
|
||||
# `event-buffer`
|
||||
|
||||
## Purpose
|
||||
|
||||
Provides the per-`(tenant, topic)` reconnect-event buffer used to replay events to a reconnecting client whose `lastEventId` precedes the current head. Two concrete implementations ship — `MemoryReconnectEventBuffer` for single-host deployments and `BrokerReconnectEventBuffer` for broker-backed multi-host fan-out — and `resolveReconnectEventBuffer` picks the right one according to the configured strategy and the broker wired into the host.
|
||||
|
||||
This module is the operating-default pin for design doc §14 open question on buffer storage: the foundation ships `"auto"` which resolves to broker-backed when a Redis broker is wired, in-memory otherwise.
|
||||
|
||||
## Features
|
||||
|
||||
- Strategy enum (`"auto" | "memory" | "broker"`) with three documented behaviours.
|
||||
- `MemoryReconnectEventBuffer` is a per-bucket ring buffer — FIFO eviction, `limit` events per `(tenant, topic)` pair.
|
||||
- `BrokerReconnectEventBuffer` maintains a local mirror so replay still works during transient broker downtime; pushes also flow to the broker on a fire-and-forget topic for peer-host mirrors.
|
||||
- `"broker"` strategy refuses boot with `WS_BUN.RECONNECT_BUFFER_MISS` when no buffer-capable broker is wired.
|
||||
|
||||
## Usage: Basic
|
||||
|
||||
```ts
|
||||
import { MemoryReconnectEventBuffer } from "@suaveplan/api-ws-bun";
|
||||
|
||||
const buf = new MemoryReconnectEventBuffer<{ value: number }>(64);
|
||||
buf.push({ id: "1", topic: "orders", tenant, payload: { value: 1 } });
|
||||
buf.push({ id: "2", topic: "orders", tenant, payload: { value: 2 } });
|
||||
const replay = buf.since(tenant, "orders", "1");
|
||||
console.log(replay.length); // 1
|
||||
```
|
||||
|
||||
## Usage: Advanced
|
||||
|
||||
```ts
|
||||
import {
|
||||
resolveReconnectEventBuffer,
|
||||
isBufferCapableBroker,
|
||||
} from "@suaveplan/api-ws-bun";
|
||||
|
||||
const buffer = resolveReconnectEventBuffer("auto", broker, 256);
|
||||
// If `broker.supportsReconnectBuffer === true`, returns a
|
||||
// BrokerReconnectEventBuffer wrapping `broker`. Otherwise returns
|
||||
// MemoryReconnectEventBuffer.
|
||||
console.log(isBufferCapableBroker(broker)); // true | false
|
||||
```
|
||||
|
||||
## API Reference
|
||||
|
||||
- `BufferedEvent<Payload>` — `{ id, topic, tenant, payload }`.
|
||||
- `ReconnectEventBuffer<Payload>` — `{ push, since, dispose }`.
|
||||
- `BufferCapableBroker<Payload>` — broker contract extension flagging buffer support.
|
||||
- `isBufferCapableBroker(broker): boolean` — discriminant.
|
||||
- `MemoryReconnectEventBuffer<Payload>` — single-host implementation.
|
||||
- `BrokerReconnectEventBuffer<Payload>` — broker-backed wrapper.
|
||||
- `resolveReconnectEventBuffer(strategy, broker, limit)` — factory.
|
||||
|
||||
## Implementation Notes
|
||||
|
||||
The memory buffer uses `Array.prototype.shift()` for eviction because the typical `limit` is small (default 256 events per `(tenant, topic)` pair), so the O(n) shift is dwarfed by the network cost of a single broadcast. A linked-list ring would micro-optimise the eviction at the cost of opaqueness; the simple array form keeps the code one screenful tall.
|
||||
|
||||
The broker wrapper performs `void this.broker.publish(...)` rather than awaiting because the buffer's contract guarantees `push` is synchronous — the caller is on the broadcast hot-path and cannot block on broker latency. Peer-host mirror sync is therefore best-effort; deployments that need strict mirror consistency configure `"broker"` against a stronger backend.
|
||||
Reference in New Issue
Block a user