167 lines
4.9 KiB
Markdown
167 lines
4.9 KiB
Markdown
# OpenSpec Change: enterprise-browser-network-discovery-peerjs
|
|
|
|
- **Change ID**: enterprise-browser-network-discovery-peerjs
|
|
- **Package**: `@suaveplan/network-discovery-peerjs`
|
|
- **Category**: browser
|
|
- **Target path**: `browser/network/network-discovery-peerjs`
|
|
- **Status**: SUPERSEDED-BY-GENESIS-WAVE
|
|
- **Date**: 2026-04-24
|
|
- **Reference spec**: `/mnt/s/web/suaveplan/enterprise/network-discovery-peerjs.md`
|
|
|
|
---
|
|
|
|
## Summary
|
|
|
|
Deliver `@suaveplan/network-discovery-peerjs` on the genesis branch at enterprise quality. The package implements `DiscoveryStrategy` for `@suaveplan/network` wrapping the PeerJS signalling client. Ships `PeerJSDiscovery`, `PeerConnectionManager`, `RoomManager`, `PeerJSEventEmitter`, `PeerJSIntervals`, and `PeerJSMessageHandlers` with strict-mode that refuses the public PeerJS cloud, Zod-validated messages, full unit tests for every module, and an ICE-passthrough config.
|
|
|
|
---
|
|
|
|
## Current-state audit (genesis)
|
|
|
|
Fresh build — does not exist on genesis yet.
|
|
|
|
---
|
|
|
|
## Available workspace deps on genesis
|
|
|
|
| Package | Role |
|
|
|---|---|
|
|
| `@suaveplan/network` (`workspace:^`) | `DiscoveryStrategy` interface |
|
|
| `@suaveplan/error` (`workspace:^`) | Typed PeerJS errors |
|
|
| `@suaveplan/types` (`workspace:^`) | `LoggerLike` |
|
|
| `@suaveplan/crypto` (`workspace:^`) | Optional signed metadata |
|
|
| `@suaveplan/schema-registry` (`workspace:^`) | Message schema registration |
|
|
| `zod` (`catalog:forms`) | `PeerJSMessage` Zod schemas |
|
|
| `@opentelemetry/api` (`catalog:observability`) | Connection/room metrics |
|
|
| `tslib` (`catalog:build`) | Runtime helpers |
|
|
|
|
External: `peerjs` (Bun catalog). React in devDeps for story.
|
|
|
|
---
|
|
|
|
## Preserved public API surface
|
|
|
|
```ts
|
|
class PeerJSDiscovery implements DiscoveryStrategy {
|
|
constructor(config: PeerJSDiscoveryConfig)
|
|
start(): Promise<void>
|
|
stop(): Promise<void>
|
|
getPeers(): PeerInfo[]
|
|
on(event: string, handler: Function): void
|
|
|
|
static selfHosted(options: { host: string; port: number; path: string; secure: boolean }): PeerJSDiscovery
|
|
}
|
|
|
|
interface PeerJSDiscoveryConfig {
|
|
host: string // Required; no default to 0.peerjs.com
|
|
port: number
|
|
path: string
|
|
secure: boolean // Must be true in production
|
|
roomId: string
|
|
iceServers?: RTCIceServer[]
|
|
strict?: boolean // Default true; rejects default cloud host
|
|
}
|
|
// + PeerJSMessage, PeerJSMessageType, PeerJSPeerMetadata
|
|
```
|
|
|
|
---
|
|
|
|
## New additions for genesis
|
|
|
|
### 1. Strict-mode gate
|
|
|
|
Refuses to start if `host` is the public PeerJS cloud (`0.peerjs.com` / `peerjs.com`) when `strict: true`.
|
|
|
|
### 2. `selfHosted` static factory
|
|
|
|
`PeerJSDiscovery.selfHosted({ host, port, path, secure })` — a self-hosting preset that enforces strict mode automatically.
|
|
|
|
### 3. Zod-validated messages
|
|
|
|
`PeerJSMessageSchema` variants for `PEER_ANNOUNCE`, `PEER_LEAVE`, `PING`, `PONG`; validated in `PeerJSMessageHandlers` with `PEERJS_MESSAGE_REJECTED` on failure.
|
|
|
|
### 4. Reconnection policy
|
|
|
|
Exponential backoff + jitter on signalling dropouts; `'connection:lost'` + `'connection:restored'` typed events.
|
|
|
|
### 5. Optional signed metadata
|
|
|
|
When `config.sign: true`, metadata signed with `@suaveplan/crypto` ed25519.
|
|
|
|
### 6. ICE server passthrough
|
|
|
|
`PeerJSDiscoveryConfig.iceServers` forwarded to PeerJS's WebRTC config.
|
|
|
|
### 7. Error codes
|
|
|
|
`PEERJS_SIGNALING_UNREACHABLE`, `PEERJS_ROOM_FULL`, `PEERJS_CONNECTION_FAILED`, `PEERJS_MESSAGE_REJECTED`.
|
|
|
|
### 8. OTel metrics
|
|
|
|
Counter `discovery.peerjs.connections_opened_total`, counter `discovery.peerjs.rooms_joined_total`, histogram `discovery.peerjs.signaling_rtt_ms`.
|
|
|
|
---
|
|
|
|
## File layout
|
|
|
|
```text
|
|
browser/network/network-discovery-peerjs/
|
|
package.json
|
|
tsconfig.json
|
|
vitest.config.ts
|
|
src/
|
|
index.ts
|
|
error-codes.ts
|
|
peerjs-discovery/
|
|
peerjs-discovery.ts
|
|
peerjs-discovery.md
|
|
peerjs-discovery.types.ts
|
|
peerjs-discovery.test.ts
|
|
index.ts
|
|
peer-connection-manager/
|
|
peer-connection-manager.ts
|
|
peer-connection-manager.md
|
|
peer-connection-manager.test.ts
|
|
index.ts
|
|
room-manager/
|
|
room-manager.ts
|
|
room-manager.md
|
|
room-manager.test.ts
|
|
index.ts
|
|
peerjs-connection/
|
|
peerjs-connection.ts
|
|
peerjs-connection.md
|
|
peerjs-connection.test.ts
|
|
index.ts
|
|
peerjs-message-handlers/
|
|
peerjs-message-handlers.ts
|
|
peerjs-message-handlers.md
|
|
peerjs-message-handlers.test.ts
|
|
index.ts
|
|
peerjs-intervals/
|
|
peerjs-intervals.ts
|
|
peerjs-intervals.md
|
|
peerjs-intervals.test.ts
|
|
index.ts
|
|
peerjs-event-emitter/
|
|
peerjs-event-emitter.ts
|
|
peerjs-event-emitter.md
|
|
peerjs-event-emitter.test.ts
|
|
index.ts
|
|
schema/
|
|
peerjs-schema/
|
|
peerjs-schema.ts
|
|
peerjs-schema.md
|
|
index.ts
|
|
tests/
|
|
integration.test.ts
|
|
```
|
|
|
|
---
|
|
|
|
## Impact
|
|
|
|
**Downstream**: `@suaveplan/network-discovery-hybrid`.
|
|
|
|
**Prerequisites**: `@suaveplan/network`, `@suaveplan/error`, `@suaveplan/crypto` on Verdaccio.
|