Files
wehub-resource-sync e30e75b5d4
Changesets / Create Version PR (push) Has been cancelled
Deploy Shadcn Registry / Deploy Production (push) Has been cancelled
Template Metrics / LOC + Bundle Size (push) Has been cancelled
Code Quality / Oxlint + Oxfmt (push) Has been cancelled
Code Quality / Template Sync (push) Has been cancelled
Code Quality / Build Changed Packages (push) Has been cancelled
Code Quality / Test Changed Packages (push) Has been cancelled
Deploy Expo Example / Deploy Production (push) Has been cancelled
Deploy Ink Example / Deploy Production (push) Has been cancelled
Python Tests / pytest (assistant-stream, 3.10) (push) Has been cancelled
Python Tests / pytest (assistant-stream, 3.12) (push) Has been cancelled
Python Tests / pytest (assistant-ui-sync-server-api, 3.10) (push) Has been cancelled
Python Tests / pytest (assistant-ui-sync-server-api, 3.12) (push) Has been cancelled
chore: import upstream snapshot with attribution
2026-07-13 13:40:13 +08:00

105 lines
3.0 KiB
TypeScript

import { describe, expect, it } from "vitest";
import { GorpRelay } from "../src/GorpRelay";
import type { GorpMessage } from "../src/Gorp";
type State = { count: number };
type Command = { type: "incCount" };
const initial = (): State => ({ count: 0 });
function recordSubscriber() {
const envs: GorpMessage[] = [];
return {
envs,
callback: (env: GorpMessage) =>
envs.push({ ops: env.ops.slice(), ack: env.ack }),
};
}
describe("GorpRelay — forwarding", () => {
it("forwards each received command via send", () => {
const sent: Command[] = [];
const relay = new GorpRelay<State, Command>({
initialState: initial(),
send: (cmd) => sent.push(cmd),
});
relay.receive({ type: "incCount" });
relay.receive({ type: "incCount" });
expect(sent).toHaveLength(2);
});
});
describe("GorpRelay — applyUpstream", () => {
it("applies ops into the state mirror and forwards them to subscribers", () => {
const relay = new GorpRelay<State, Command>({
initialState: initial(),
send: () => {},
});
const sub = recordSubscriber();
relay.subscribe(sub.callback);
relay.applyUpstream({
ops: [{ type: "set", path: ["count"], value: 7 }],
});
expect(relay.state.count).toBe(7);
expect(sub.envs[0]!.ops).toEqual([
{ type: "set", path: ["count"], value: 7 },
]);
});
it("forwards ack verbatim to subscribers", () => {
const relay = new GorpRelay<State, Command>({
initialState: initial(),
send: () => {},
});
const sub = recordSubscriber();
relay.subscribe(sub.callback);
relay.applyUpstream({ ops: [], ack: 5 });
expect(sub.envs[0]).toEqual({ ops: [], ack: 5 });
});
it("synchronous emit — no microtask delay", () => {
const relay = new GorpRelay<State, Command>({
initialState: initial(),
send: () => {},
});
const sub = recordSubscriber();
relay.subscribe(sub.callback);
relay.applyUpstream({ ops: [{ type: "set", path: ["count"], value: 1 }] });
// No `await flushMicrotasks` — already there.
expect(sub.envs).toHaveLength(1);
});
it("suppresses fully-empty envelopes", () => {
const relay = new GorpRelay<State, Command>({
initialState: initial(),
send: () => {},
});
const sub = recordSubscriber();
relay.subscribe(sub.callback);
relay.applyUpstream({ ops: [] });
expect(sub.envs).toHaveLength(0);
});
});
describe("GorpRelay — persistence", () => {
it("round-trips state", () => {
const relay = new GorpRelay<State, Command>({
initialState: initial(),
send: () => {},
});
relay.applyUpstream({
ops: [{ type: "set", path: ["count"], value: 5 }],
});
const serialized = relay.serialize();
expect(serialized.state).toEqual({ count: 5 });
const fresh = new GorpRelay<State, Command>({
initialState: initial(),
send: () => {},
});
fresh.restore(serialized);
expect(fresh.state).toEqual({ count: 5 });
});
});