From f4a9788f2d5c69b14ba0a646ac68a5078fc338db Mon Sep 17 00:00:00 2001 From: online5880 Date: Mon, 9 Mar 2026 22:08:50 +0900 Subject: [PATCH] fix: tighten Windows adapter command handling --- packages/adapter-utils/src/server-utils.ts | 4 ++-- pnpm-lock.yaml | 13 ++++++++++++- server/package.json | 1 + .../codex-local-adapter-environment.test.ts | 6 +++--- 4 files changed, 18 insertions(+), 6 deletions(-) diff --git a/packages/adapter-utils/src/server-utils.ts b/packages/adapter-utils/src/server-utils.ts index 8a296191..3d273cd9 100644 --- a/packages/adapter-utils/src/server-utils.ts +++ b/packages/adapter-utils/src/server-utils.ts @@ -136,7 +136,7 @@ function windowsPathExts(env: NodeJS.ProcessEnv): string[] { async function pathExists(candidate: string) { try { - await fs.access(candidate, fsConstants.X_OK); + await fs.access(candidate, process.platform === "win32" ? fsConstants.F_OK : fsConstants.X_OK); return true; } catch { return false; @@ -173,7 +173,7 @@ async function resolveCommandPath(command: string, cwd: string, env: NodeJS.Proc function quoteForCmd(arg: string) { if (!arg.length) return '""'; - const escaped = arg.replace(/"/g, '""').replace(/%/g, "%%"); + const escaped = arg.replace(/"/g, '""'); return /[\s"&<>|^()]/.test(escaped) ? `"${escaped}"` : escaped; } diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index 80270207..ff1442a2 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -321,6 +321,9 @@ importers: '@types/ws': specifier: ^8.18.1 version: 8.18.1 + cross-env: + specifier: ^10.1.0 + version: 10.1.0 supertest: specifier: ^7.0.0 version: 7.2.2 @@ -8930,6 +8933,14 @@ snapshots: chai: 5.3.3 tinyrainbow: 2.0.0 + '@vitest/mocker@3.2.4(vite@7.3.1(@types/node@24.12.0)(jiti@2.6.1)(lightningcss@1.30.2)(tsx@4.21.0))': + dependencies: + '@vitest/spy': 3.2.4 + estree-walker: 3.0.3 + magic-string: 0.30.21 + optionalDependencies: + vite: 7.3.1(@types/node@24.12.0)(jiti@2.6.1)(lightningcss@1.30.2)(tsx@4.21.0) + '@vitest/mocker@3.2.4(vite@7.3.1(@types/node@25.2.3)(jiti@2.6.1)(lightningcss@1.30.2)(tsx@4.21.0))': dependencies: '@vitest/spy': 3.2.4 @@ -11707,7 +11718,7 @@ snapshots: dependencies: '@types/chai': 5.2.3 '@vitest/expect': 3.2.4 - '@vitest/mocker': 3.2.4(vite@7.3.1(@types/node@25.2.3)(jiti@2.6.1)(lightningcss@1.30.2)(tsx@4.21.0)) + '@vitest/mocker': 3.2.4(vite@7.3.1(@types/node@24.12.0)(jiti@2.6.1)(lightningcss@1.30.2)(tsx@4.21.0)) '@vitest/pretty-format': 3.2.4 '@vitest/runner': 3.2.4 '@vitest/snapshot': 3.2.4 diff --git a/server/package.json b/server/package.json index 2b3e1ed0..73fda4bd 100644 --- a/server/package.json +++ b/server/package.json @@ -61,6 +61,7 @@ "@types/node": "^24.6.0", "@types/supertest": "^6.0.2", "@types/ws": "^8.18.1", + "cross-env": "^10.1.0", "supertest": "^7.0.0", "tsx": "^4.19.2", "typescript": "^5.7.3", diff --git a/server/src/__tests__/codex-local-adapter-environment.test.ts b/server/src/__tests__/codex-local-adapter-environment.test.ts index bf42e47d..a9201c98 100644 --- a/server/src/__tests__/codex-local-adapter-environment.test.ts +++ b/server/src/__tests__/codex-local-adapter-environment.test.ts @@ -4,6 +4,8 @@ import os from "node:os"; import path from "node:path"; import { testEnvironment } from "@paperclipai/adapter-codex-local/server"; +const itWindows = process.platform === "win32" ? it : it.skip; + describe("codex_local environment diagnostics", () => { it("creates a missing working directory when cwd is absolute", async () => { const cwd = path.join( @@ -30,9 +32,7 @@ describe("codex_local environment diagnostics", () => { await fs.rm(path.dirname(cwd), { recursive: true, force: true }); }); - it("runs the hello probe when Codex is available via a Windows .cmd wrapper", async () => { - if (process.platform !== "win32") return; - + itWindows("runs the hello probe when Codex is available via a Windows .cmd wrapper", async () => { const root = path.join( os.tmpdir(), `paperclip-codex-local-probe-${Date.now()}-${Math.random().toString(16).slice(2)}`,