diff --git a/config/scripts/ci-shard-timings.json b/config/scripts/ci-shard-timings.json index b05a20a560e..38153d24ff6 100644 --- a/config/scripts/ci-shard-timings.json +++ b/config/scripts/ci-shard-timings.json @@ -1475,7 +1475,6 @@ "src/main/claude-usage/transcript-tuple-append.test.ts": 454, "src/main/claude-usage/worktree-attribution-scaling.test.ts": 43, "src/main/claude/agent-view-bridge.test.ts": 126, - "src/main/claude/agent-view-hook-install.test.ts": 250, "src/main/claude/agent-view-install.test.ts": 259, "src/main/claude/agent-view-mod-source.test.ts": 733, "src/main/claude/agent-view-service.test.ts": 305, @@ -2026,7 +2025,6 @@ "src/main/crash-reporting/renderer-recovery-circuit-breaker.test.ts": 48, "src/main/crash-reporting/self-initiated-tree-kill-log.test.ts": 171, "src/main/crash-reporting/suppressed-process-gone-breadcrumb.test.ts": 40, - "src/main/credential-file-protection.test.ts": 24, "src/main/credentials/saved-credential-readability.test.ts": 48, "src/main/cursor/hook-command.live-shell.test.ts": 408, "src/main/cursor/hook-service.test.ts": 588, @@ -2789,7 +2787,6 @@ "src/main/ipc/agent-pane-retirement-ipc.test.ts": 84, "src/main/ipc/agent-session-attachment-upload.test.ts": 153, "src/main/ipc/ai-vault-host-leg-cache-retention.test.ts": 1958, - "src/main/ipc/ai-vault-resume-chat-copy.test.ts": 1331, "src/main/ipc/ai-vault-resume.test.ts": 918, "src/main/ipc/ai-vault-scan-coalescing.test.ts": 4631, "src/main/ipc/ai-vault-search-all-hosts-real-index.test.ts": 1536, @@ -5668,7 +5665,6 @@ "src/main/runtime/rpc/worktree-ps-other-client-marks.test.ts": 92, "src/main/runtime/rpc/worktree-removal-marker-projection.test.ts": 348, "src/main/runtime/rpc/ws-empty-payload-frame-write.test.ts": 95, - "src/main/runtime/rpc/ws-fallback-port-store.test.ts": 33, "src/main/runtime/rpc/ws-transport-accept-order.test.ts": 67, "src/main/runtime/rpc/ws-transport-static-web.test.ts": 117, "src/main/runtime/rpc/ws-transport-transient-packet-loss.test.ts": 50, diff --git a/src/main/claude/agent-view-hook-install.test.ts b/src/main/claude/agent-view-hook-install.test.ts deleted file mode 100644 index 99c932d7987..00000000000 --- a/src/main/claude/agent-view-hook-install.test.ts +++ /dev/null @@ -1,46 +0,0 @@ -import { mkdirSync, mkdtempSync, readFileSync, rmSync, writeFileSync } from 'node:fs' -import { tmpdir } from 'node:os' -import { join } from 'node:path' -import { afterEach, expect, it, vi } from 'vitest' -import { createAgentHookMemorySftp } from '../agent-hooks/agent-hook-memory-sftp.test-fixture' -import { ClaudeHookService } from './hook-service' - -const roots: string[] = [] -afterEach(() => { - vi.restoreAllMocks() - vi.unstubAllEnvs() - roots.splice(0).forEach((root) => rmSync(root, { recursive: true, force: true })) -}) - -it('keeps local hooks installed when the optional mod cannot be written', () => { - const root = mkdtempSync(join(tmpdir(), 'orca-agent-view-hook-install-')) - roots.push(root) - vi.stubEnv('HOME', root) - vi.stubEnv('USERPROFILE', root) - vi.spyOn(console, 'warn').mockImplementation(() => {}) - mkdirSync(join(root, '.claude')) - writeFileSync(join(root, '.claude', 'skills'), 'blocked') - - const status = new ClaudeHookService().install({ claudeVersion: '2.1.309' }) - - expect(status).toMatchObject({ state: 'installed', managedHooksPresent: true, detail: null }) - const settings = JSON.parse(readFileSync(join(root, '.claude', 'settings.json'), 'utf8')) - expect(settings.hooks.Stop).toHaveLength(1) - expect(readFileSync(join(root, '.claude', 'skills'), 'utf8')).toBe('blocked') -}) - -it('keeps remote hooks installed when optional mod discovery fails', async () => { - const memory = createAgentHookMemorySftp() - vi.spyOn(console, 'warn').mockImplementation(() => {}) - vi.spyOn(memory.sftp, 'readdir').mockImplementation(() => { - throw new Error('SFTP directory access denied') - }) - - const status = await new ClaudeHookService().installRemote(memory.sftp, '/home/remote', { - claudeVersion: '2.1.309' - }) - - expect(status).toMatchObject({ state: 'installed', managedHooksPresent: true, detail: null }) - const settings = JSON.parse(memory.fs.files.get('/home/remote/.claude/settings.json') ?? '{}') - expect(settings.hooks.Stop).toHaveLength(1) -}) diff --git a/src/main/credential-file-protection.test.ts b/src/main/credential-file-protection.test.ts deleted file mode 100644 index 6ef22fb809d..00000000000 --- a/src/main/credential-file-protection.test.ts +++ /dev/null @@ -1,46 +0,0 @@ -import { beforeEach, describe, expect, it, vi } from 'vitest' - -const existsSyncMock = vi.hoisted(() => vi.fn()) -const readFileSyncMock = vi.hoisted(() => vi.fn()) -vi.mock('node:fs', () => ({ existsSync: existsSyncMock, readFileSync: readFileSyncMock })) - -const { readCredentialFileProtection } = await import('./credential-file-protection') - -describe('readCredentialFileProtection', () => { - beforeEach(() => { - existsSyncMock.mockReset() - readFileSyncMock.mockReset() - }) - - it('reports null when the file does not exist', () => { - existsSyncMock.mockReturnValue(false) - expect(readCredentialFileProtection('/tokens/linear')).toBeNull() - expect(readFileSyncMock).not.toHaveBeenCalled() - }) - - it('reports null for an empty file, which reads as no credential at all', () => { - existsSyncMock.mockReturnValue(true) - readFileSyncMock.mockReturnValue(Buffer.alloc(0)) - expect(readCredentialFileProtection('/tokens/linear')).toBeNull() - }) - - it('reports plaintext for a bare token', () => { - existsSyncMock.mockReturnValue(true) - readFileSyncMock.mockReturnValue(Buffer.from('lin_api_abcdef123456', 'utf8')) - expect(readCredentialFileProtection('/tokens/linear')).toBe('plaintext') - }) - - it('reports sealed for ciphertext', () => { - existsSyncMock.mockReturnValue(true) - readFileSyncMock.mockReturnValue(Buffer.from([0x76, 0x31, 0x30, 0x00, 0x8f, 0x02, 0x1c])) - expect(readCredentialFileProtection('/tokens/linear')).toBe('sealed') - }) - - it('reports null when the file cannot be read rather than guessing', () => { - existsSyncMock.mockReturnValue(true) - readFileSyncMock.mockImplementation(() => { - throw Object.assign(new Error('EACCES'), { code: 'EACCES' }) - }) - expect(readCredentialFileProtection('/tokens/linear')).toBeNull() - }) -}) diff --git a/src/main/ipc/ai-vault-resume-chat-copy.test.ts b/src/main/ipc/ai-vault-resume-chat-copy.test.ts deleted file mode 100644 index 9f38fbf24e2..00000000000 --- a/src/main/ipc/ai-vault-resume-chat-copy.test.ts +++ /dev/null @@ -1,52 +0,0 @@ -import { afterEach, describe, expect, it, vi } from 'vitest' -import { setStructuredAgentSessionHost } from '../native-chat/agent-session-wire/structured-agent-session-registry' -import { installCopyingChat } from '../ai-vault/structured-session-ownership.test-support' -import type { AiVaultPrepareSessionResumeArgs } from '../../shared/ai-vault-resume-preparation' - -vi.mock('electron', () => ({ ipcMain: { handle: vi.fn() } })) - -const { prepareAiVaultSessionResume } = await import('./ai-vault-resume') - -const OMP_ID = '019fd611-2b3c-7d4e-9f50-6b7c8d9e0f1a' -const forkArgs = ( - executionHostId: AiVaultPrepareSessionResumeArgs['executionHostId'] -): AiVaultPrepareSessionResumeArgs => ({ - agent: 'omp', - sessionId: OMP_ID, - filePath: `/Users/me/.omp/agent/sessions/--repo--/x_${OMP_ID}.jsonl`, - codexHome: null, - executionHostId, - fork: true -}) - -afterEach(() => setStructuredAgentSessionHost(null)) - -describe('Resume in New CLI preparation for a chat whose host makes the copy', () => { - it('leaves the copy to the server that runs a remote chat', async () => { - const copy = vi.fn(async () => ({ - sessionId: 'local-copy' - })) - installCopyingChat({ transport: 'acp', agent: 'omp', nativeId: 'unrelated' }, copy) - const prepareRuntimeSessionResume = vi.fn(async () => ({ - useRealCodexHome: false, - forkedSession: { - sessionId: 'remote-copy', - filePath: '/sessions/remote-copy.jsonl', - agent: 'omp' as const - } - })) - - await expect( - prepareAiVaultSessionResume(forkArgs('runtime:env-1'), { prepareRuntimeSessionResume }) - ).resolves.toEqual({ - useRealCodexHome: false, - forkedSession: { - sessionId: 'remote-copy', - filePath: '/sessions/remote-copy.jsonl', - agent: 'omp' - } - }) - expect(prepareRuntimeSessionResume).toHaveBeenCalledWith('env-1', forkArgs('runtime:env-1')) - expect(copy).not.toHaveBeenCalled() - }) -}) diff --git a/src/main/runtime/rpc/ws-fallback-port-store.test.ts b/src/main/runtime/rpc/ws-fallback-port-store.test.ts deleted file mode 100644 index 48b8e4ef422..00000000000 --- a/src/main/runtime/rpc/ws-fallback-port-store.test.ts +++ /dev/null @@ -1,56 +0,0 @@ -import { mkdtempSync, writeFileSync } from 'node:fs' -import { tmpdir } from 'node:os' -import { join } from 'node:path' -import { describe, expect, it } from 'vitest' -import { - clearWsFallbackPort, - readWsFallbackPort, - wsFallbackPortLadder, - writeWsFallbackPort -} from './ws-fallback-port-store' - -function makeUserDataPath(): string { - return mkdtempSync(join(tmpdir(), 'ws-fallback-port-test-')) -} - -describe('ws-fallback-port-store', () => { - it('builds a deterministic ladder above the preferred port, none for an OS-assigned one', () => { - // 6769 stays free for a `pnpm dev` instance pinned beside packaged Orca. - expect(wsFallbackPortLadder(6768)).toEqual(Array.from({ length: 30 }, (_, i) => 6770 + i)) - expect(wsFallbackPortLadder(6769)).toEqual(Array.from({ length: 31 }, (_, i) => 6770 + i)) - expect(wsFallbackPortLadder(65530)).toEqual([65531, 65532, 65533, 65534, 65535]) - expect(wsFallbackPortLadder(0)).toEqual([]) - }) - - it('clears a persisted fallback port', () => { - const userDataPath = makeUserDataPath() - writeWsFallbackPort(userDataPath, 54321) - clearWsFallbackPort(userDataPath) - expect(readWsFallbackPort(userDataPath)).toBeUndefined() - expect(() => clearWsFallbackPort(userDataPath)).not.toThrow() - }) - - it('round-trips a persisted fallback port', () => { - const userDataPath = makeUserDataPath() - expect(readWsFallbackPort(userDataPath)).toBeUndefined() - writeWsFallbackPort(userDataPath, 54321) - expect(readWsFallbackPort(userDataPath)).toBe(54321) - }) - - it('ignores corrupt or invalid contents', () => { - const userDataPath = makeUserDataPath() - writeFileSync(join(userDataPath, 'mobile-ws-fallback-port.json'), 'not json', 'utf8') - expect(readWsFallbackPort(userDataPath)).toBeUndefined() - writeFileSync(join(userDataPath, 'mobile-ws-fallback-port.json'), '{"port":-4}', 'utf8') - expect(readWsFallbackPort(userDataPath)).toBeUndefined() - writeFileSync(join(userDataPath, 'mobile-ws-fallback-port.json'), '{"port":"80"}', 'utf8') - expect(readWsFallbackPort(userDataPath)).toBeUndefined() - }) - - it('refuses to persist an invalid port', () => { - const userDataPath = makeUserDataPath() - writeWsFallbackPort(userDataPath, 0) - writeWsFallbackPort(userDataPath, 70000) - expect(readWsFallbackPort(userDataPath)).toBeUndefined() - }) -}) diff --git a/src/main/ssh/orcad-node-runtime-install-options.test.ts b/src/main/ssh/orcad-node-runtime-install-options.test.ts deleted file mode 100644 index 2ae90271339..00000000000 --- a/src/main/ssh/orcad-node-runtime-install-options.test.ts +++ /dev/null @@ -1,40 +0,0 @@ -import { describe, expect, it, vi } from 'vitest' -import { materializeNodeRuntimeArchive } from '../node-runtime/pinned-runtime-materializer' -import { orcadNodeRuntimeInstallOptions } from './orcad-node-runtime-install-options' -import { WSL_NODE_RUNTIME_DOWNLOAD_BUDGET } from '../wsl/wsl-node-runtime-download-budget' - -vi.mock('../node-runtime/pinned-runtime-materializer', () => ({ - materializeNodeRuntimeArchive: vi.fn(async () => '/cache/node/archives/node.tar.xz'), - nodeRuntimeArchiveCachePath: () => '/cache/node/archives/node.tar.xz' -})) - -describe('orcadNodeRuntimeInstallOptions', () => { - it('leaves SSH deploys on the default download timing', async () => { - const options = orcadNodeRuntimeInstallOptions('linux-x64-glibc', '/cache', {}) - expect(options.nodeRuntimeHostConnectTimeoutSeconds).toBeUndefined() - await options.nodeRuntimeArchive() - expect(vi.mocked(materializeNodeRuntimeArchive).mock.lastCall?.[2]).toEqual({ - signal: undefined, - connectTimeoutMs: undefined - }) - }) - - it('bounds both the desktop and the host download for a WSL deploy', async () => { - const options = orcadNodeRuntimeInstallOptions('linux-x64-glibc', '/cache', { - nodeRuntimeDownload: WSL_NODE_RUNTIME_DOWNLOAD_BUDGET - }) - expect(options.nodeRuntimeHostConnectTimeoutSeconds).toBe(15) - expect(options.nodeRuntimeOfflineArchivePath).toBe('/cache/node/archives/node.tar.xz') - await options.nodeRuntimeArchive() - expect(vi.mocked(materializeNodeRuntimeArchive).mock.lastCall?.[2]).toMatchObject({ - connectTimeoutMs: 15_000 - }) - }) - - it('fails a dead network within about 45 s: one desktop attempt, then official and mirror on the host', () => { - const worstCaseMs = - WSL_NODE_RUNTIME_DOWNLOAD_BUDGET.desktopConnectTimeoutMs + - 2 * WSL_NODE_RUNTIME_DOWNLOAD_BUDGET.hostConnectTimeoutSeconds * 1000 - expect(worstCaseMs).toBeLessThanOrEqual(45_000) - }) -}) diff --git a/src/renderer/src/components/plugins/presentation/plugin-contributions.test.ts b/src/renderer/src/components/plugins/presentation/plugin-contributions.test.ts deleted file mode 100644 index 3b1208809c3..00000000000 --- a/src/renderer/src/components/plugins/presentation/plugin-contributions.test.ts +++ /dev/null @@ -1,41 +0,0 @@ -import { describe, expect, it } from 'vitest' -import { - describePluginContributions, - EMPTY_CONTRIBUTION_SOURCE, - uncoveredCatalogTypes -} from './plugin-contributions' - -describe('plugin contributions', () => { - it('names each contribution with what kind it is', () => { - const rows = describePluginContributions({ - ...EMPTY_CONTRIBUTION_SOURCE, - themes: [{ id: 'midnight', label: 'Midnight', base: 'dark' }], - iconThemes: [{ id: 'minimal', label: 'Minimal Icons' }], - syntaxes: [ - { - id: 'gleam', - label: 'Gleam', - extensions: ['.gleam', '.glm', '.a', '.b', '.c'], - filenames: [] - } - ], - vmRecipes: ['Ubuntu dev'] - }) - expect(rows.map((row) => [row.title, row.detail])).toEqual([ - ['Midnight', 'App theme · Dark'], - ['Minimal Icons', 'File icon theme'], - ['Gleam', 'Syntax highlighting · .gleam, .glm, .a, .b +1'], - ['Ubuntu dev', 'Machine recipe'] - ]) - }) - - it('falls back to catalog types only for what nothing names', () => { - const rows = describePluginContributions({ - ...EMPTY_CONTRIBUTION_SOURCE, - themes: [{ id: 'midnight', label: 'Midnight' }] - }) - expect( - uncoveredCatalogTypes(['app-theme', 'terminal-theme', 'instructions', 'worker'], rows, true) - ).toEqual(['terminal-theme']) - }) -})