From 50805d89776cf2eeda5b4b09a947d08aec3fed4b Mon Sep 17 00:00:00 2001 From: Peter Steinberger Date: Thu, 19 Feb 2026 08:43:35 +0000 Subject: [PATCH] test(agents): dedupe patch and cli credential assertions --- src/agents/apply-patch.e2e.test.ts | 41 +++++++++++++++++---------- src/agents/cli-credentials.test.ts | 45 +++++++++++------------------- 2 files changed, 43 insertions(+), 43 deletions(-) diff --git a/src/agents/apply-patch.e2e.test.ts b/src/agents/apply-patch.e2e.test.ts index 99990fcb82..5a2dae87e7 100644 --- a/src/agents/apply-patch.e2e.test.ts +++ b/src/agents/apply-patch.e2e.test.ts @@ -13,6 +13,23 @@ async function withTempDir(fn: (dir: string) => Promise) { } } +function buildAddFilePatch(targetPath: string): string { + return `*** Begin Patch +*** Add File: ${targetPath} ++escaped +*** End Patch`; +} + +async function expectOutsideWriteRejected(params: { + dir: string; + patchTargetPath: string; + outsidePath: string; +}) { + const patch = buildAddFilePatch(params.patchTargetPath); + await expect(applyPatch(patch, { cwd: params.dir })).rejects.toThrow(/Path escapes sandbox root/); + await expect(fs.readFile(params.outsidePath, "utf8")).rejects.toBeDefined(); +} + describe("applyPatch", () => { it("adds a file", async () => { await withTempDir(async (dir) => { @@ -79,14 +96,12 @@ describe("applyPatch", () => { ); const relativeEscape = path.relative(dir, escapedPath); - const patch = `*** Begin Patch -*** Add File: ${relativeEscape} -+escaped -*** End Patch`; - try { - await expect(applyPatch(patch, { cwd: dir })).rejects.toThrow(/Path escapes sandbox root/); - await expect(fs.readFile(escapedPath, "utf8")).rejects.toBeDefined(); + await expectOutsideWriteRejected({ + dir, + patchTargetPath: relativeEscape, + outsidePath: escapedPath, + }); } finally { await fs.rm(escapedPath, { force: true }); } @@ -97,14 +112,12 @@ describe("applyPatch", () => { await withTempDir(async (dir) => { const escapedPath = path.join(os.tmpdir(), `openclaw-apply-patch-${Date.now()}.txt`); - const patch = `*** Begin Patch -*** Add File: ${escapedPath} -+escaped -*** End Patch`; - try { - await expect(applyPatch(patch, { cwd: dir })).rejects.toThrow(/Path escapes sandbox root/); - await expect(fs.readFile(escapedPath, "utf8")).rejects.toBeDefined(); + await expectOutsideWriteRejected({ + dir, + patchTargetPath: escapedPath, + outsidePath: escapedPath, + }); } finally { await fs.rm(escapedPath, { force: true }); } diff --git a/src/agents/cli-credentials.test.ts b/src/agents/cli-credentials.test.ts index ad62fd6773..909d69ff38 100644 --- a/src/agents/cli-credentials.test.ts +++ b/src/agents/cli-credentials.test.ts @@ -5,6 +5,7 @@ import { afterEach, beforeEach, describe, expect, it, vi } from "vitest"; const execSyncMock = vi.fn(); const execFileSyncMock = vi.fn(); +const CLI_CREDENTIALS_CACHE_TTL_MS = 15 * 60 * 1000; function mockExistingClaudeKeychainItem() { execFileSyncMock.mockImplementation((file: unknown, args: unknown) => { @@ -31,6 +32,16 @@ function getAddGenericPasswordCall() { ); } +async function readCachedClaudeCliCredentials(allowKeychainPrompt: boolean) { + const { readClaudeCliCredentialsCached } = await import("./cli-credentials.js"); + return readClaudeCliCredentialsCached({ + allowKeychainPrompt, + ttlMs: CLI_CREDENTIALS_CACHE_TTL_MS, + platform: "darwin", + execSync: execSyncMock, + }); +} + describe("cli credentials", () => { beforeEach(() => { vi.useFakeTimers(); @@ -189,20 +200,8 @@ describe("cli credentials", () => { vi.setSystemTime(new Date("2025-01-01T00:00:00Z")); - const { readClaudeCliCredentialsCached } = await import("./cli-credentials.js"); - - const first = readClaudeCliCredentialsCached({ - allowKeychainPrompt: true, - ttlMs: 15 * 60 * 1000, - platform: "darwin", - execSync: execSyncMock, - }); - const second = readClaudeCliCredentialsCached({ - allowKeychainPrompt: false, - ttlMs: 15 * 60 * 1000, - platform: "darwin", - execSync: execSyncMock, - }); + const first = await readCachedClaudeCliCredentials(true); + const second = await readCachedClaudeCliCredentials(false); expect(first).toBeTruthy(); expect(second).toEqual(first); @@ -222,23 +221,11 @@ describe("cli credentials", () => { vi.setSystemTime(new Date("2025-01-01T00:00:00Z")); - const { readClaudeCliCredentialsCached } = await import("./cli-credentials.js"); + const first = await readCachedClaudeCliCredentials(true); - const first = readClaudeCliCredentialsCached({ - allowKeychainPrompt: true, - ttlMs: 15 * 60 * 1000, - platform: "darwin", - execSync: execSyncMock, - }); + vi.advanceTimersByTime(CLI_CREDENTIALS_CACHE_TTL_MS + 1); - vi.advanceTimersByTime(15 * 60 * 1000 + 1); - - const second = readClaudeCliCredentialsCached({ - allowKeychainPrompt: true, - ttlMs: 15 * 60 * 1000, - platform: "darwin", - execSync: execSyncMock, - }); + const second = await readCachedClaudeCliCredentials(true); expect(first).toBeTruthy(); expect(second).toBeTruthy();