From 0724ca8783a87f3da5e3221e666eee2a291fafeb Mon Sep 17 00:00:00 2001 From: JATMN Date: Thu, 22 Oct 2026 14:47:51 -0700 Subject: [PATCH] test: restore leaked module mocks behind the remaining non-isolated shard failures (TA-001 round 2) (#2341) * test: restore leaked module mocks behind the remaining non-isolated shard failures (TA-001 round 2) * test: restore real sessionStorage after resume tests (TA-001 round 2) --- .../setupGitHubActions.test.ts | 7 +++++ src/commands/replay/replay.test.tsx | 30 ++++++++++++++----- src/commands/resume/resume.test.tsx | 5 ++++ src/hooks/useApiKeyVerification.test.tsx | 8 +++-- .../AgentTool/runAgent.persistence.test.ts | 11 +++++-- .../BashTool/bashCommandAnalysis.test.ts | 6 +++- 6 files changed, 55 insertions(+), 12 deletions(-) diff --git a/src/commands/install-github-app/setupGitHubActions.test.ts b/src/commands/install-github-app/setupGitHubActions.test.ts index b7e114170..212a411ad 100644 --- a/src/commands/install-github-app/setupGitHubActions.test.ts +++ b/src/commands/install-github-app/setupGitHubActions.test.ts @@ -6,6 +6,7 @@ import { } from '../../test/sharedMutationLock.js' type BrowserModule = typeof import('../../utils/browser.js') +type ConfigModule = typeof import('../../utils/config.js') type ExecFileNoThrowModule = typeof import('../../utils/execFileNoThrow.js') type ExecCall = { @@ -15,6 +16,7 @@ type ExecCall = { type RealModules = { browser: BrowserModule + config: ConfigModule execFileNoThrow: ExecFileNoThrowModule } @@ -44,6 +46,9 @@ async function importRealModules(): Promise { browser: (await import( `../../utils/browser.ts?setup-actions-real-${cacheKey}` )) as BrowserModule, + config: { + ...await import(`../../utils/config.js?real=${cacheKey}`), + } as ConfigModule, execFileNoThrow: (await import( `../../utils/execFileNoThrow.ts?setup-actions-real-${cacheKey}` )) as ExecFileNoThrowModule, @@ -212,6 +217,8 @@ afterEach(() => { try { mock.restore() if (realModules) { + mock.module('src/utils/config.js', () => realModules!.config) + mock.module('../../utils/config.js', () => realModules!.config) mock.module( '../../utils/execFileNoThrow.js', () => realModules!.execFileNoThrow, diff --git a/src/commands/replay/replay.test.tsx b/src/commands/replay/replay.test.tsx index 7bfa6e17c..af55570e3 100644 --- a/src/commands/replay/replay.test.tsx +++ b/src/commands/replay/replay.test.tsx @@ -10,13 +10,29 @@ import { AppStateProvider } from '../../state/AppState.js' import type { LogOption, ReplayIndex } from '../../types/logs.js' import { renderToString } from '../../utils/staticRender.js' import * as realBootstrapState from '../../bootstrap/state.js' -import * as realGetWorktreePaths from '../../utils/getWorktreePaths.js' -import * as realSessionStorage from '../../utils/sessionStorage.js' -import * as realReplayIndex from '../../utils/replayIndex.js' -import * as realUseTerminalSize from '../../hooks/useTerminalSize.js' -import * as realModalContext from '../../context/modalContext.js' -import * as realLogSelector from '../../components/LogSelector.js' -import * as realReplayTimeline from './ReplayTimeline.js' + +const nonce = `${Date.now()}-${Math.random()}` +const realGetWorktreePaths = { + ...await import(`../../utils/getWorktreePaths.js?real=${nonce}`), +} +const realSessionStorage = { + ...await import(`../../utils/sessionStorage.js?real=${nonce}`), +} +const realReplayIndex = { + ...await import(`../../utils/replayIndex.js?real=${nonce}`), +} +const realUseTerminalSize = { + ...await import(`../../hooks/useTerminalSize.js?real=${nonce}`), +} +const realModalContext = { + ...await import(`../../context/modalContext.js?real=${nonce}`), +} +const realLogSelector = { + ...await import(`../../components/LogSelector.js?real=${nonce}`), +} +const realReplayTimeline = { + ...await import(`./ReplayTimeline.js?real=${nonce}`), +} type LogSelectorProps = { logs: LogOption[] diff --git a/src/commands/resume/resume.test.tsx b/src/commands/resume/resume.test.tsx index fc8e91c4b..a71849c8e 100644 --- a/src/commands/resume/resume.test.tsx +++ b/src/commands/resume/resume.test.tsx @@ -18,6 +18,10 @@ import type { LocalJSXCommandOnDone, } from '../../types/command.js' +const realSessionStorage = { + ...await import(`../../utils/sessionStorage.js?real=${Date.now()}-${Math.random()}`), +} + type OnDoneArgs = Parameters let saveGoalStateMock: ReturnType @@ -196,6 +200,7 @@ describe('/resume and /continue unified command', () => { afterEach(() => { mock.restore() + mock.module('../../utils/sessionStorage.js', () => realSessionStorage) }) test('/continue continues an active goal', async () => { diff --git a/src/hooks/useApiKeyVerification.test.tsx b/src/hooks/useApiKeyVerification.test.tsx index 3b41fe576..0c21b7e3e 100644 --- a/src/hooks/useApiKeyVerification.test.tsx +++ b/src/hooks/useApiKeyVerification.test.tsx @@ -3,8 +3,6 @@ import { PassThrough } from 'node:stream' import { afterAll, afterEach, beforeEach, expect, mock, test } from 'bun:test' import React from 'react' import { createRoot, Text } from '../ink.js' -import * as realState from '../bootstrap/state.js' -import * as realClaudeApi from '../services/api/claude.js' import { acquireSharedMutationLock, releaseSharedMutationLock, @@ -14,6 +12,12 @@ const nonce = `${Date.now()}-${Math.random()}` const realAuth = { ...await import(`../utils/auth.js?real=${nonce}`), } +const realState = { + ...await import(`../bootstrap/state.js?real=${nonce}`), +} +const realClaudeApi = { + ...await import(`../services/api/claude.js?real=${nonce}`), +} type AuthState = { anthropicAuthEnabled: boolean diff --git a/src/tools/AgentTool/runAgent.persistence.test.ts b/src/tools/AgentTool/runAgent.persistence.test.ts index 6f4d260f4..afa1fcae9 100644 --- a/src/tools/AgentTool/runAgent.persistence.test.ts +++ b/src/tools/AgentTool/runAgent.persistence.test.ts @@ -2,8 +2,13 @@ import { afterEach, beforeEach, expect, mock, test } from 'bun:test' import type { AgentDefinition } from './loadAgentsDir.js' import type { ToolUseContext } from '../../Tool.js' -const actualSessionStorage = { ...await import('../../utils/sessionStorage.js') } -const actualQuery = { ...await import('../../query.js') } +const nonce = `${Date.now()}-${Math.random()}` +const actualSessionStorage = { + ...await import(`../../utils/sessionStorage.js?real=${nonce}`), +} +const actualQuery = { + ...await import(`../../query.js?real=${nonce}`), +} // Track how many times each storage function is called let metadataWriteCount = 0 @@ -16,6 +21,8 @@ beforeEach(() => { afterEach(() => { mock.restore() + mock.module('../../utils/sessionStorage.js', () => actualSessionStorage) + mock.module('../../query.js', () => actualQuery) }) /** Load runAgent with a failing metadata writer while retaining unrelated module exports. */ diff --git a/src/tools/BashTool/bashCommandAnalysis.test.ts b/src/tools/BashTool/bashCommandAnalysis.test.ts index c1e61efcc..3e50a9f65 100644 --- a/src/tools/BashTool/bashCommandAnalysis.test.ts +++ b/src/tools/BashTool/bashCommandAnalysis.test.ts @@ -5,9 +5,13 @@ import { } from '../../test/sharedMutationLock.js' import { parseForSecurityFromAst } from '../../utils/bash/ast.js' import { PARSE_ABORTED } from '../../utils/bash/parser.js' -import * as realDebug from '../../utils/debug.js' import { analyzeBashCommand } from './bashCommandAnalysis.js' +const nonce = `${Date.now()}-${Math.random()}` +const realDebug = { + ...await import(`../../utils/debug.js?real=${nonce}`), +} + let importCounter = 0 beforeEach(async () => {