# Test kit (`orca/testing`) `ORCA plugin test` runs `*.test.ts(x)` files in Node with `orca` and `orca/testing` resolved to what this Orca ships, and plugin sources (panels and the worker `main`) loaded as Orca loads them. Every act resolves once the panel or worker has settled: `await` it and never add sleeps. ## Functions - `function mockHost(options?: MockHostOptions): MockHost`: A stand-in Orca host that refuses what Orca refuses, with the same codes: a missing capability, bad params, a method panels cannot call, and a user-gesture method (`shell.openExternal`, `files.saveAs`) without a press first. - `function hostError(code: string, message?: string, retryAfterMs?: number): HostError` - `function mockEditorHost(file: MockEditorFile, options?: MockEditorHostOptions): MockEditorHost`: A stand-in for Orca's custom editor host, backed by an in-memory file: installs `globalThis.orca` with the real frame shell's document API and `session()`, so sync logic tests in Node. Answers only document calls. One at a time: a new one disposes the last. - `function stored(value: unknown, version: number): unknown`: A persisted value an older version wrote, to test an atom's `migrate`. - `function mount(target: PanelModule | (() => OrcaNode), options?: MountOptions): Promise`: Mounts a panel module (`import * as panel from './panel'`) or its component, with the real runtime and Orca's own checks, and resolves once it has drawn. Mounting again starts over: every atom goes back to its initial value. - `function mountWorker(module: WorkerModule, options?: MountWorkerOptions): Promise`: Calls the worker's default-exported `activate(orca)` with the `orca` object Orca passes, backed by `mockHost` (worker methods, the manifest's capabilities). `.ts` mains load as Orca loads them. - `function defineCheck>(scenarios: S): S`: Named scenarios for `orca plugin check`, as the default export of `.check.ts` beside the panel (`src/panel.check.ts` for `src/panel.tsx`). Check renders the panel once per scenario, with the plugin's worker on the same host; without the file it renders once with defaults. - `function test(name: string, fn: () => unknown): Promise`: Node's `node:test`, re-exported so a test type-checks without the Node typings. - `function describe(name: string, fn: () => unknown): Promise` - `function beforeEach(fn: () => unknown): void` - `function afterEach(fn: () => unknown): void` ## `TestPanel` (from `mount`) - `host: MockHost` - `errors: readonly PanelIssue[]` - `warnings: readonly string[]`: Props and components Orca would drop, as Orca would warn. - `refusals: readonly MockHostRefusal[]`: Host calls Orca would refuse (a missing capability, no press), even ones the panel caught. - `persisted: { plugin: Record; workspace: Record; storage: Record }`: What persisted atoms hold now, by scope and key; `storage` is the plugin's storage. - `find(query: TestQuery)`: The innermost match, or null. - `findAll(query: TestQuery)` - `tree()`: The drawn tree as plain data, for snapshots; handlers show as `[handler]`. - `summary()`: One line per thing a person notices first: headings, callouts, empty states, table and tree sizes, the selected tab, loading placeholders, danger or warning text and boxes. - `press(target: Target)`: Each act grants one gesture (a press) and resolves once the panel has settled. - `type(target: Target, text: string, options?: { replace?: boolean; submit?: boolean })`: Types after what the field holds (`replace` clears it first); `submit` presses Enter. - `submit(target: Target)` - `toggle(target: Target)`: A Switch, Checkbox or Collapsible. - `select(target: Target, value: string)`: A Select or RadioGroup option, or a Tabs tab, by value. - `slide(target: Target, value: number)` - `sort(target: Target, column: string)`: Table: a header click (ascending first, then flipping). - `selectRows(target: Target, keys: readonly string[])`: Table: replaces the selection with exactly these rows. - `activateRow(target: Target, key: string)`: Table: Enter or a double click on a row. - `loadMore(target: Target)`: Table: scrolls to the end of the loaded rows (needs `hasMore` and `onLoadMore`). - `expand(target: Target, key: string)`: Tree: expand or collapse an item, calling `onToggle`. - `collapse(target: Target, key: string)` - `selectItem(target: Target, key: string)` - `activateItem(target: Target, key: string)` - `expandedOf(target: Target)`: Tree: the items Orca shows expanded. - `columnsOf(target: Target, view?: { width?: number })`: Table: the column keys Orca shows at `width` px (wide when omitted), after `hideBelow`. - `rowsOf(target: Target)`: Table: row keys in the order Orca draws them. - `valueOf(target: Target)`: What Orca shows in a value control: text, a flag, a number, a tab, or selected keys. - `emit(event: E, payload: OrcaEvents[E])`: An Orca event: `theme`, or a workspace or agent event the panel subscribed to. - `post(event: K, payload: PluginPanelEvents[K])`: What the plugin's worker posts with `orca.panels.post`; `plugin.on` handlers hear it. - `post(event: Undeclared, payload?: JsonValue)` - `setVisible(visible: boolean)` - `rerender()` - `settled()` - `unmount()`: Ends the run: setup cleanup, `ctx.signal` and subscriptions, as when the panel closes. ## `TestWorker` (from `mountWorker`) - `host: MockHost` - `logs: readonly string[]`: What the worker passed to `orca.log`. - `refusals: readonly MockHostRefusal[]` - `posts: readonly { event: string; payload?: unknown; panel?: string }[]`: What the worker sent with `orca.panels.post`, in order. - `emit(event: E, payload: PluginEvents[E])`: Delivers an event as Orca would (checked against Orca's payload schema) and waits for every handler. - `hooks: { fire(hook: H, event: PluginHooks[H]['event']): Promise> }` - `command(commandId: string, args?: unknown)`: Runs a registered command and resolves with its result. - `request(name: K, input?: PluginRequestInput, caller?: { panel?: string })`: A panel's `plugin.request`, answered by the worker's `orca.panels.handle`; `panel` names the calling panel's contribution id. An unhandled name rejects with `unknown_method`. - `request(name: Undeclared, input?: JsonValue, caller?: { panel?: string })` - `deactivate()`: Runs the module's `deactivate` and drops its handlers. ## `MockHost` (from `mockHost`) - `calls: readonly { method: string; params: unknown }[]`: Every call that reached the host, in order, refused ones included. - `refusals: readonly MockHostRefusal[]`: `capability_denied`, `not_permitted`, `invalid_params` or `unknown_method` calls. - `callsOf(method: string)` - `respond(method: string, result: unknown)` - `data()`: The plugin's storage, settings and secrets as they are now. ## `MockEditorHost` (from `mockEditorHost`) - `orca: OrcaFrameApi`: The frame API, also installed as `globalThis.orca`. - `text: string | undefined`: The file as Orca holds it now; undefined for a bytes file. - `bytes: Uint8Array | undefined` - `version: number`: Rises with each document sent to the editor. - `edits: readonly MockEditorEdit[]`: Every `applyEdit`, in order, refused ones included. - `replace(next: string | ArrayBuffer | Uint8Array)`: An outside change, such as an agent writing the file. - `conflictNext(outside?: string | ArrayBuffer | Uint8Array)`: Refuses the next edit with `conflict`, after landing `outside` first when given. - `flush()`: As a save does: asks the editor for pending edits and waits for its answer (1 s); rejects, as Orca refuses to save, after an edit too large to apply. - `setTheme(colorScheme: 'light' | 'dark')` - `dispose()`: Removes `globalThis.orca`. ## Options - `MountOptions = { host?: MockHost; theme?: 'light' | 'dark'; locale?: string; visible?: boolean; panelId?: string; persisted?: { plugin?: Record; workspace?: Record } }` - `MountWorkerOptions = { host?: MockHost; events?: readonly string[]; commands?: readonly string[]; hooks?: readonly (string | { event: string; onError?: 'pass' | 'deny' })[] }` - `MockHostOptions = { capabilities?: readonly string[]; results?: Record; requests?: MockRequests; storage?: Record; settings?: Record; secrets?: Record }` - `MockEditorHostOptions = { readOnly?: boolean; colorScheme?: 'light' | 'dark'; locale?: string; fileType?: string }` - `CheckScenario = MockHostOptions & { persisted?: MountOptions['persisted']; theme?: 'light' | 'dark'; events?: readonly { [E in keyof OrcaEvents]: { event: E; payload: OrcaEvents[E] } }[keyof OrcaEvents][] }`