Files
SnapOtter/packages/doc-engine/tests/helpers/spawn-capture.ts
T
SnapOtterandGitHub 301e6eb01a test: coverage campaign and mutation testing across five packages (#628)
Coverage 83.6 to 87.36% lines, 81.63 to 84.14% branches. Mutation testing across five packages: image-engine 85, media-engine 92, doc-engine 87, shared+enterprise 86, apps/api security and jobs slice. Runs all five lanes weekly. Fixes the silently-broken mutation CI (babel pin), a redact-pdf envelope-shape test bug, an untested enterprise license valid-signature path, and an audit test that only exercised a hand-copied reproduction. Test and config only, no product code changes beyond the babel pin and one test-only oidc export. Full suite: 16,712 pass, 0 fail.
2026-07-24 17:36:57 +08:00

56 lines
1.9 KiB
TypeScript

import type { spawn } from "node:child_process";
import type { Mock } from "vitest";
import { createFakeChild, type FakeChild, settleClose, settleError } from "./fake-child.js";
/**
* Helpers over a mocked `spawn` for the doc-engine CLI wrappers. All of them
* spawn(bin, args, opts), pipe stdout/stderr, and settle on close/error, so a
* single set of helpers drives every wrapper's success and failure paths and
* exposes the exact argv for assertion.
*/
export function makeSpawnHelpers(mockSpawn: Mock<typeof spawn>) {
/** Program the next spawn to close with the given code/output. */
function nextClose(
opts: { stdout?: string; stderr?: string; code?: number | null; signal?: string | null } = {},
): void {
mockSpawn.mockImplementationOnce(() => {
const child = createFakeChild();
settleClose(child, opts);
return child as never;
});
}
/** Program the next spawn to emit an error event. */
function nextError(err: Error): void {
mockSpawn.mockImplementationOnce(() => {
const child = createFakeChild();
settleError(child, err);
return child as never;
});
}
/** Program the next spawn to hand back a child that never settles on its own. */
function nextManual(): FakeChild {
const child = createFakeChild();
mockSpawn.mockImplementationOnce(() => child as never);
return child;
}
function lastCall(): [string, string[], Record<string, unknown>] {
const calls = mockSpawn.mock.calls;
const c = calls[calls.length - 1];
return [c[0] as string, c[1] as string[], c[2] as Record<string, unknown>];
}
function lastBin(): string {
return lastCall()[0];
}
function lastArgs(): string[] {
return lastCall()[1];
}
function lastOpts(): Record<string, unknown> {
return lastCall()[2];
}
return { nextClose, nextError, nextManual, lastCall, lastBin, lastArgs, lastOpts };
}