From 572bde869e2c98139a06ae7ef8b4046a3d494bc3 Mon Sep 17 00:00:00 2001 From: Neil <4138956+nwparker@users.noreply.github.com> Date: Fri, 16 Oct 2026 08:15:05 -0700 Subject: [PATCH] test: avoid full runtime imports in RPC boundary tests (#29721) --- .../repository-project-operations.spec.ts | 4 +++ .../files-read-dir-remote-budget.test.ts | 16 ++++++--- src/main/runtime/rpc/methods/pairing.test.ts | 6 ++-- src/main/runtime/rpc/methods/repo.test.ts | 33 +++++++++++-------- .../rpc/runtime-source-admission.test.ts | 9 +++-- 5 files changed, 46 insertions(+), 22 deletions(-) diff --git a/src/main/runtime/orca-runtime-tests/repository-project-operations.spec.ts b/src/main/runtime/orca-runtime-tests/repository-project-operations.spec.ts index 31294118b60..8c9f018f97a 100644 --- a/src/main/runtime/orca-runtime-tests/repository-project-operations.spec.ts +++ b/src/main/runtime/orca-runtime-tests/repository-project-operations.spec.ts @@ -634,6 +634,10 @@ describe('OrcaRuntimeService', () => { }) .catch((error: unknown) => error) + expect(() => runtime.addSshRepo({ connectionId: 'openclaw' })).toThrow( + 'SSH connection "openclaw" not found or not connected' + ) + // Why: the defect was a silent local clone/probe recorded as remote, not a bad message, // so the absent side effects are asserted before the wording. Both calls are awaited // first so a regression reports the corruption rather than stopping at the first throw. diff --git a/src/main/runtime/rpc/methods/files-read-dir-remote-budget.test.ts b/src/main/runtime/rpc/methods/files-read-dir-remote-budget.test.ts index 42b04ba07d6..554323dffeb 100644 --- a/src/main/runtime/rpc/methods/files-read-dir-remote-budget.test.ts +++ b/src/main/runtime/rpc/methods/files-read-dir-remote-budget.test.ts @@ -1,7 +1,7 @@ import '../unused-default-rpc-methods.test-fixture' import { describe, expect, it, vi } from 'vitest' import { RpcDispatcher } from '../dispatcher' -import { OrcaRuntimeService } from '../../orca-runtime' +import type { OrcaRuntimeService } from '../../orca-runtime' import type { DirEntry } from '../../../../shared/filesystem-entry-types' import { FILE_METHODS } from './files' @@ -12,9 +12,17 @@ const HUGE_LISTING: DirEntry[] = Array.from({ length: 80_000 }, (_, index) => ({ })) function dispatcherWithListing(entries: DirEntry[]) { - const runtime = new OrcaRuntimeService() - vi.spyOn(runtime, 'readFileExplorerDir').mockResolvedValue(entries) - return new RpcDispatcher({ runtime, methods: FILE_METHODS }) + const runtime: Pick = { + getRuntimeId: () => 'test-runtime', + readFileExplorerDir: vi + .fn() + .mockResolvedValue(entries) + } + return new RpcDispatcher({ + // oxlint-disable-next-line typescript/consistent-type-assertions -- SAFETY: files.readDir uses readFileExplorerDir; its response envelope reads only getRuntimeId. + runtime: runtime as OrcaRuntimeService, + methods: FILE_METHODS + }) } async function readDir(clientKind: 'runtime' | undefined) { diff --git a/src/main/runtime/rpc/methods/pairing.test.ts b/src/main/runtime/rpc/methods/pairing.test.ts index 05f896dec4c..95cef0c8a4b 100644 --- a/src/main/runtime/rpc/methods/pairing.test.ts +++ b/src/main/runtime/rpc/methods/pairing.test.ts @@ -1,6 +1,6 @@ import '../unused-default-rpc-methods.test-fixture' import { describe, expect, it, vi } from 'vitest' -import { OrcaRuntimeService } from '../../orca-runtime' +import type { OrcaRuntimeService } from '../../orca-runtime' import { RpcDispatcher } from '../dispatcher' import { PAIRING_METHODS } from './pairing' @@ -10,8 +10,10 @@ function dispatchPairing( pairing: NonNullable[2]>['pairing'] ): Promise> { return new Promise((resolve) => { + const runtime = { getRuntimeId: () => 'test-runtime' } const dispatcher = new RpcDispatcher({ - runtime: new OrcaRuntimeService(), + // oxlint-disable-next-line typescript/consistent-type-assertions -- SAFETY: Pairing handlers use the supplied pairing context; the envelope reads only getRuntimeId. + runtime: runtime as OrcaRuntimeService, methods: PAIRING_METHODS }) void dispatcher.dispatchStreaming( diff --git a/src/main/runtime/rpc/methods/repo.test.ts b/src/main/runtime/rpc/methods/repo.test.ts index 7b97d225554..77e504faff4 100644 --- a/src/main/runtime/rpc/methods/repo.test.ts +++ b/src/main/runtime/rpc/methods/repo.test.ts @@ -2,7 +2,7 @@ import '../unused-default-rpc-methods.test-fixture' import { describe, expect, it, vi } from 'vitest' import { RpcDispatcher } from '../dispatcher' import type { RpcRequest } from '../core' -import { OrcaRuntimeService } from '../../orca-runtime' +import type { OrcaRuntimeService } from '../../orca-runtime' import { REPO_METHODS } from './repo' import { NATIVE_REMOTE_RUNTIME_CLIENT_CAPABILITIES, @@ -18,6 +18,16 @@ function makeRequest(method: string, params?: unknown): RpcRequest { return { id: 'req-1', authToken: 'tok', method, params } } +function repoDispatcher( + runtime: Pick & Partial +) { + return new RpcDispatcher({ + // oxlint-disable-next-line typescript/consistent-type-assertions -- SAFETY: These RPC cases supply every runtime method their handlers and envelope access. + runtime: runtime as OrcaRuntimeService, + methods: REPO_METHODS + }) +} + describe('repo RPC methods', () => { it('advertises qualified-ref support from hosts and native remote clients', () => { expect(RUNTIME_CAPABILITIES).toContain(REPO_SEARCH_QUALIFIED_REFS_RUNTIME_CAPABILITY) @@ -179,10 +189,9 @@ describe('repo RPC methods', () => { connectionId: 'ssh-p8', kind: 'git' as const } - const runtime = new OrcaRuntimeService(null) - const addSshRepo = vi.spyOn(runtime, 'addSshRepo').mockResolvedValue(repo) - const addRepo = vi.spyOn(runtime, 'addRepo') - const dispatcher = new RpcDispatcher({ runtime, methods: REPO_METHODS }) + const addSshRepo = vi.fn().mockResolvedValue(repo) + const addRepo = vi.fn() + const dispatcher = repoDispatcher({ getRuntimeId: () => 'test-runtime', addSshRepo, addRepo }) const response = await dispatcher.dispatch( makeRequest('repo.addRemote', { connectionId: 'ssh-p8', remotePath: '/srv/project' }), @@ -195,9 +204,8 @@ describe('repo RPC methods', () => { }) it('refuses a remote project without an SSH target rather than adding a server path', async () => { - const runtime = new OrcaRuntimeService(null) - const addSshRepo = vi.spyOn(runtime, 'addSshRepo') - const dispatcher = new RpcDispatcher({ runtime, methods: REPO_METHODS }) + const addSshRepo = vi.fn() + const dispatcher = repoDispatcher({ getRuntimeId: () => 'test-runtime', addSshRepo }) const response = await dispatcher.dispatch( makeRequest('repo.addRemote', { remotePath: '/srv/project' }) @@ -502,8 +510,7 @@ describe('repo RPC methods', () => { }) it('persists normalized ghAccount bindings and clear sentinels', async () => { - const runtime = new OrcaRuntimeService(null) - vi.spyOn(runtime, 'updateRepo').mockResolvedValue({ + const updateRepo = vi.fn().mockResolvedValue({ id: 'repo-1', path: '/srv/repo', displayName: 'repo', @@ -511,7 +518,7 @@ describe('repo RPC methods', () => { addedAt: 0, ghAccount: { host: 'github.com', user: 'Alice' } }) - const dispatcher = new RpcDispatcher({ runtime, methods: REPO_METHODS }) + const dispatcher = repoDispatcher({ getRuntimeId: () => 'test-runtime', updateRepo }) const response = await dispatcher.dispatch( makeRequest('repo.update', { @@ -521,7 +528,7 @@ describe('repo RPC methods', () => { { clientCapabilities: [WORKTREE_VISIBILITY_DEFAULTS_RUNTIME_CAPABILITY] } ) - expect(runtime.updateRepo).toHaveBeenCalledWith('repo-1', { + expect(updateRepo).toHaveBeenCalledWith('repo-1', { ghAccount: { host: 'github.com', user: 'Alice' } }) expect(response).toMatchObject({ @@ -535,7 +542,7 @@ describe('repo RPC methods', () => { updates: { ghAccount: null } }) ) - expect(runtime.updateRepo).toHaveBeenLastCalledWith('repo-1', { ghAccount: null }) + expect(updateRepo).toHaveBeenLastCalledWith('repo-1', { ghAccount: null }) }) it('persists agent worktree visibility updates', async () => { diff --git a/src/main/runtime/rpc/runtime-source-admission.test.ts b/src/main/runtime/rpc/runtime-source-admission.test.ts index 1cfaca8ffdf..e588c56cf25 100644 --- a/src/main/runtime/rpc/runtime-source-admission.test.ts +++ b/src/main/runtime/rpc/runtime-source-admission.test.ts @@ -1,7 +1,8 @@ import './unused-default-rpc-methods.test-fixture' +import { randomUUID } from 'node:crypto' import { z } from 'zod' import { afterEach, describe, expect, it, vi } from 'vitest' -import { OrcaRuntimeService } from '../orca-runtime' +import type { OrcaRuntimeService } from '../orca-runtime' import { publishHostDescriptor } from '../host-descriptor' import { defineMethod, type RpcRequest } from './core' import { RpcDispatcher } from './dispatcher' @@ -19,7 +20,8 @@ describe('runtime source admission', () => { }) function createHarness(installationId: string | null = SOURCE_A) { - const runtime = new OrcaRuntimeService() + const id = randomUUID() + const runtime = { getRuntimeId: () => id } const runtimeId = runtime.getRuntimeId() if (installationId) { publishHostDescriptor(runtimeId, { installationId }) @@ -27,7 +29,8 @@ describe('runtime source admission', () => { } const effect = vi.fn(() => ({ sent: true })) const dispatcher = new RpcDispatcher({ - runtime, + // oxlint-disable-next-line typescript/consistent-type-assertions -- SAFETY: The fixture handler is effect; admission and response metadata read only getRuntimeId. + runtime: runtime as OrcaRuntimeService, methods: [ defineMethod({ name: 'terminal.send',