first commit

This commit is contained in:
2026-05-29 08:20:56 +01:00
commit 949299f58d
6368 changed files with 527176 additions and 0 deletions

View File

@@ -0,0 +1,93 @@
# `protocol`
<!-- begin:auto-docs -->
_(no submodules)_
<!-- end:auto-docs -->
## Purpose
Defines the wire-format of every message that crosses a `MessagePort`
between an `api-host` and an isolated/sandboxed plugin worker. The
package exports a Zod-validated discriminated union (`WorkerRpcFrame`)
plus individual frame schemas so receivers fail loudly on malformed
input rather than silently corrupting state.
Every wire payload is JSON-clone-safe (no functions, classes, or
symbols at the top level) and carries an explicit `v` field so the host
and worker can negotiate version-skew at handshake time. The current
protocol version is `"1.0.0"`; future incompatible changes bump the
major.
## Features
- Ten frame kinds: `request`, `response` (ok/error), `cancel`,
`progress`, `stream-open`, `stream-chunk`, `stream-end` (ok/error),
`stream-ack`, `hello`, `goodbye`.
- Recursive Zod schema for the error envelope including bounded cause
chains (depth checked at the reconstruction layer, not the wire).
- `parseFrame(input)` performs full validation; the inferred return
type is the typed union usable in `switch (frame.kind)`.
- Branded correlation-id alignment with `@suaveplan/api-types`'s
`WorkerRpcCorrelationId` numeric brand.
## Usage: Basic
```ts
import { parseFrame, PROTOCOL_VERSION } from "@suaveplan/api-worker-rpc/protocol";
const frame = parseFrame(rawMessage);
if (frame.kind === "request") {
handleRequest(frame.id, frame.method, frame.params);
}
```
## Usage: Advanced
```ts
import {
type WorkerRpcFrame,
workerRpcFrameSchema,
requestFrameSchema,
} from "@suaveplan/api-worker-rpc/protocol";
// Pre-validate a specific kind without the full union:
const req = requestFrameSchema.parse(payload);
// Or guard via the union for exhaustive dispatch:
function dispatch(frame: WorkerRpcFrame) {
switch (frame.kind) {
case "request":
case "stream-open":
// ...
break;
case "response":
if (frame.ok) handleSuccess(frame.result);
else handleError(frame.error);
break;
// ...
}
}
```
## API Reference
- `PROTOCOL_VERSION: "1.0.0"` — the version literal embedded in every
outbound frame.
- `workerRpcFrameSchema` — the top-level discriminated union schema.
- `requestFrameSchema`, `responseFrameSchema`, etc. — individual
schemas for each frame kind.
- `parseFrame(input: unknown): WorkerRpcFrame` — validates and returns
the typed frame; throws `ZodError` on failure.
- `ErrorEnvelope` — interface for serialised errors carried over the
wire (used by `error-reconstruction`).
## Implementation Notes
- The error envelope schema is recursive (`z.lazy`) so cause chains
can nest arbitrarily — depth bounding is the receiver's job.
- The `v` field is a free-form string at the schema layer; clients
and servers reject mismatches via the `VERSION_MISMATCH` code so
the same frame can be parsed for diagnostic logging even when
it is too new to handle.
- `response` and `stream-end` are themselves discriminated by `ok`,
giving compilers exhaustive narrowing on success vs. error tails.