Initial Commit

This commit is contained in:
2026-05-27 23:29:53 +01:00
commit fbc70f96e6
10000 changed files with 1102152 additions and 0 deletions

View File

@@ -0,0 +1,166 @@
# OpenSpec Change: enterprise-browser-network-discovery-hybrid
- **Change ID**: enterprise-browser-network-discovery-hybrid
- **Package**: `@suaveplan/network-discovery-hybrid`
- **Category**: browser
- **Target path**: `browser/network/network-discovery-hybrid`
- **Status**: SUPERSEDED-BY-GENESIS-WAVE
- **Date**: 2026-04-24
- **Reference spec**: `/mnt/s/web/suaveplan/enterprise/network-discovery-hybrid.md`
---
## Summary
Deliver `@suaveplan/network-discovery-hybrid` on the genesis branch at enterprise quality. The package composes any subset of the sibling discovery strategies into a single `HybridDiscoveryManager` with priority-based peer selection, health tracking per strategy, automatic fallback, and de-duplicated peer sets. No `__mocks__/` directory, no `vi.stubGlobal`, no `any` — tests exercise real `DiscoveryStrategy` implementations from sibling packages installed as devDependencies.
---
## 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 hybrid errors |
| `@suaveplan/types` (`workspace:^`) | `LoggerLike` |
| `@suaveplan/schema-registry` (`workspace:^`) | Config schema registration |
| `zod` (`catalog:forms`) | `HybridDiscoveryConfig` schema |
| `@opentelemetry/api` (`catalog:observability`) | Strategy health metrics |
| `tslib` (`catalog:build`) | Runtime helpers |
Optional peer deps (devDependencies for tests): `@suaveplan/network-discovery-peerjs`, `@suaveplan/network-discovery-trystero`, `@suaveplan/network-discovery-webtorrent`, `@suaveplan/network-discovery-crdt`, `@suaveplan/network-discovery-gundb`.
Dev: `vitest`, `@vitest/coverage-istanbul`, `@suaveplan/testing`. React in devDeps for story.
---
## Preserved public API surface (from main branch)
```ts
class HybridDiscoveryManager {
constructor(config: HybridDiscoveryConfig)
start(): Promise<void>
stop(): Promise<void>
getPeers(): PeerInfo[]
getStrategyHealth(): Record<string, StrategyHealth>
addStrategy(config: StrategyConfig): void
removeStrategy(id: string): void
on(event: HybridDiscoveryEvent, handler: Function): void
static presets: {
browserP2P(): HybridDiscoveryConfig
}
}
interface HybridDiscoveryConfig {
strategies: StrategyConfig[]
fallbackOrder?: string[]
deduplicatePeers?: boolean
}
interface StrategyConfig { id: string; strategy: DiscoveryStrategy; priority: StrategyPriority; enabled?: boolean }
interface StrategyHealth { status: 'healthy' | 'degraded' | 'failed'; peersDiscovered: number; lastError?: Error }
type StrategyPriority = 'high' | 'medium' | 'low' | number
type HybridDiscoveryEvent = 'peer:discovered' | 'peer:left' | 'strategy:health:change' | 'strategy:failover' | 'error'
// + PeerSource, HybridManagerStatus
```
---
## New additions for genesis
### 1. No `__mocks__/` — real implementations
Tests install sibling discovery packages as `devDependencies` and instantiate real `DiscoveryStrategy` objects. A minimal in-tree `MemoryDiscoveryStrategy` (implements the real interface, not duck-typed) is provided for unit tests.
### 2. `HybridDiscoveryConfig` Zod schema
Full config validation; registered in `@suaveplan/schema-registry`.
### 3. Typed `StrategyLoadError`
When a peer-dep strategy is missing, `strategy-loader.ts` returns a typed `STRATEGY_LOAD_FAILED` error — never fails silently.
### 4. Deterministic priority tie-breaking
Equal-priority strategies are ranked alphabetically by `id`.
### 5. Back-pressure
Configurable `maxPeerEventsPerSecond` per strategy; excess events queued or dropped with counter metric.
### 6. `HybridDiscoveryManager.presets.browserP2P()`
One-liner wiring PeerJS + Trystero with sensible defaults.
### 7. Error codes
`STRATEGY_LOAD_FAILED`, `STRATEGY_UNAVAILABLE`, `HYBRID_NO_HEALTHY_STRATEGY`.
### 8. OTel metrics
Counter `discovery.hybrid.strategy_healthy`, counter `discovery.hybrid.strategy_degraded`, counter `discovery.hybrid.strategy_failed`; histogram `discovery.hybrid.failover_ms`.
---
## File layout
```text
browser/network/network-discovery-hybrid/
package.json
tsconfig.json
vitest.config.ts
src/
index.ts
error-codes.ts
hybrid-discovery-manager/
hybrid-discovery-manager.ts
hybrid-discovery-manager.md
hybrid-discovery-manager.types.ts
hybrid-discovery-manager.test.ts
index.ts
strategy-manager/
strategy-manager.ts
strategy-manager.md
strategy-manager.test.ts
index.ts
strategy-loader/
strategy-loader.ts
strategy-loader.md
strategy-loader.test.ts
index.ts
lifecycle/
lifecycle.ts
lifecycle.md
lifecycle.test.ts
index.ts
peer-tracker/
peer-tracker.ts
peer-tracker.md
peer-tracker.test.ts
index.ts
presets/
presets.ts
presets.md
index.ts
internal/
memory-discovery-strategy.ts (test double implementing real interface)
tests/
config.test.ts
config-advanced.test.ts
runtime.test.ts (split ≤500 lines)
runtime-failover.test.ts
```
---
## Impact
**Downstream**: top-level P2P networking clients.
**Prerequisites**: `@suaveplan/network`, `@suaveplan/error` on Verdaccio; sibling discovery packages as devDeps.

View File

@@ -0,0 +1,104 @@
# Tasks: enterprise-browser-network-discovery-hybrid
**Change ID**: enterprise-browser-network-discovery-hybrid
**Package**: `@suaveplan/network-discovery-hybrid`
**Target path**: `browser/network/network-discovery-hybrid`
**Prerequisite packages on Verdaccio**: `@suaveplan/network`, `@suaveplan/error`, `@suaveplan/types`
---
## 1. Scaffold
- [x] Create directory tree per `proposal.md`.
- [x] `package.json` at version `0.1.0`, `"sideEffects": false`.
- `dependencies`: `@suaveplan/network workspace:^`, `@suaveplan/error workspace:^`, `@suaveplan/types workspace:^`, `zod catalog:forms`, `@opentelemetry/api catalog:observability`, `tslib catalog:build`
- `peerDependencies` + `peerDependenciesMeta.optional: true`: `@suaveplan/network-discovery-peerjs`, `@suaveplan/network-discovery-trystero`, `@suaveplan/network-discovery-webtorrent`, `@suaveplan/network-discovery-crdt`, `@suaveplan/network-discovery-gundb`
- `devDependencies`: above five sibling packages as `workspace:^`, `vitest catalog:testing`, `@vitest/coverage-istanbul catalog:testing`, `@suaveplan/testing workspace:^`, `react catalog:browser`, `@types/react catalog:browser`
- [x] `tsconfig.json`, `vitest.config.ts` (pool: forks).
---
## 2. Error codes
- [x] `STRATEGY_LOAD_FAILED`, `STRATEGY_UNAVAILABLE`, `HYBRID_NO_HEALTHY_STRATEGY`.
- [x] `registerHybridErrorCodes()` — call eagerly.
---
## 3. In-tree `MemoryDiscoveryStrategy` (`src/internal/memory-discovery-strategy.ts`)
- [x] Implement a minimal `DiscoveryStrategy` for unit tests — typed correctly against the real interface, no duck typing.
---
## 4. `PeerTracker` (`src/peer-tracker/`)
- [x] Implement deduplication of peer sets across strategies; track `PeerSource` per peer.
- [x] Write `peer-tracker.test.ts`, `peer-tracker.md`.
---
## 5. `StrategyLoader` (`src/strategy-loader/`)
- [x] Implement dynamic peer-dep loading: check if the package is present in the module graph; return `STRATEGY_LOAD_FAILED` typed error if missing — never returns `null` silently.
- [x] Write `strategy-loader.test.ts`, `strategy-loader.md`.
---
## 6. `StrategyManager` (`src/strategy-manager/`)
- [x] Implement health tracking, priority tie-breaking (alphabetical on equal score), back-pressure per strategy.
- [x] Wire OTel counters for strategy health transitions.
- [x] Write `strategy-manager.test.ts`, `strategy-manager.md`.
---
## 7. `Lifecycle` (`src/lifecycle/`)
- [x] Implement start/stop sequencing across all strategies with timeout per strategy.
- [x] Wire OTel histogram `discovery.hybrid.failover_ms`.
- [x] Write `lifecycle.test.ts`, `lifecycle.md`.
---
## 8. `HybridDiscoveryManager` (`src/hybrid-discovery-manager/`)
- [x] Implement orchestrator composing all sub-modules.
- [x] `static presets.browserP2P()` returning a `HybridDiscoveryConfig` wiring PeerJS + Trystero.
- [x] Write `hybrid-discovery-manager.test.ts`, `hybrid-discovery-manager.md`, `hybrid-discovery-manager.types.ts`.
---
## 9. Presets (`src/presets/`)
- [x] Implement `presets` object with `browserP2P()`.
- [x] Write `presets.md`.
---
## 10. Tests (all ≤500 lines each)
- [x] `tests/config.test.ts` — config schema validation.
- [x] `tests/config-advanced.test.ts` — priority ordering, back-pressure, tie-breaking.
- [x] `tests/runtime.test.ts` — start/stop, failover, peer dedup.
- [x] `tests/runtime-failover.test.ts` — strategy degraded → failover → recovery.
- [x] All tests use real `MemoryDiscoveryStrategy` or real sibling packages — no `__mocks__/`.
---
## 11. Zod schema + docs
- [x] `HybridDiscoveryConfigSchema`; register in `@suaveplan/schema-registry`.
- [x] Story (`src/hybrid-discovery-manager/hybrid-discovery.stories.tsx`) with React devDep declared.
- [x] Write `.md` per module; `README.md` with sibling install matrix.
---
## 12. Verify and publish
- [x] `bunx turbo lint typecheck test --filter=@suaveplan/network-discovery-hybrid` — green.
- [x] `bunx turbo test:coverage` — 100%.
- [x] No `__mocks__/` directory, no `vi.mock`, no `any`.
- [x] Missing-peer-dep scenario returns typed error (not silent null).
- [x] `bun scripts/publish.ts --package @suaveplan/network-discovery-hybrid`.
- [x] Archive to `openspec/archive/2026-04-24-enterprise-browser-network-discovery-hybrid/`.