拓冰建站拓冰建站
首页 / 资讯中心 / 正文

oh-my-openagent 的 Windows Codex CI 稳定性修复:lsp-tools-mcp 测试环境隔离实战解析

oh-my-openagent 的 Windows Codex CI 稳定性修复lsp-tools-mcp 测试环境隔离实战解析【免费下载链接】oh-my-openagentOmO: Just type mass ulw keyword with your prompt. Now you are the master of graph engineering.项目地址: https://gitcode.com/gh_mirrors/oh/oh-my-openagent导读本文围绕 oh-my-openagent 仓库中一次真实的 Windows CI 稳定性修复PR 6611 的codex-compatibility (windows-latest)作业展开完整还原了从失败复现、根因定位、测试隔离修复到真实 Codex 运行验证的全过程。读完本文你将掌握跨平台 MCP 测试中常见的两类环境泄漏问题——PATH 可执行文件泄漏与 cwd/home 配置泄漏——的识别方法与隔离手段并理解createSpawnCommand在 Windows 下的命令解析原理及 codex-qa mock 模型的端到端验证思路。一、背景一次只在 Windows 上失败的 CI 作业PR 6611 的 GitHub 运行run31760176754job94644705178中只有codex-compatibility (windows-latest)一个作业失败其余平台与阶段均通过。这类仅 Windows 失败的现象通常指向平台相关的环境差异而不是业务逻辑回归——因为同样的代码在 Linux/macOS 上全部通过。修复前的本地复现数据显示了失败规模在 LSP 包的第一轮全量门禁中结果是93 通过、1 跳过、3 失败。更关键的是涉及的文件在打补丁前与upstream/dev逐字节一致说明这是一个早已存在、依赖宿主环境的测试缺陷而非运行时回退runtime-fallback的生产回归——修复补丁只改测试不改生产代码。二、失败复现与最小化隔离修复团队首先在本地完整复现了 GitHub 上的失败作业命令链条与仓库根目录package.json中的test:codex脚本保持一致该脚本依次执行 codex-install、git-bash-mcp、lsp-tools-mcp、lsp-daemon 的构建随后运行 LSP 包测试、omo-codex 插件测试与若干安装器测试# 1. 复现失败的 GitHub 作业完整命令链 bun run test:codex # 2. 隔离出失败的具体包并单独跑测试 npm --prefix packages/lsp-tools-mcp test # 3. 运行包级静态门禁 npm --prefix packages/lsp-tools-mcp run typecheck npx biome check test/process.test.ts test/mcp.test.ts test/client-wrapper.test.ts这种先全量复现、再逐层隔离的路径是定位跨平台问题的标准做法先用test:codex确认失败可复现再收窄到packages/lsp-tools-mcp这个包其package.json中定义了test: vitest --run、typecheck: tsc --noEmit、lint: biome check .最后精确到三个测试文件把排查范围从整条流水线压缩到几十个用例。三、根因定位两类环境泄漏3.1 PATH 可执行文件泄漏createSpawnCommand的期望值被宿主环境污染第一个根因指向测试对createSpawnCommand的断言。该函数位于 packages/lsp-core/src/lsp/process.tslsp-tools-mcp通过 packages/lsp-tools-mcp/src/lsp/process.ts 直接 re-export其职责是把命令 参数整理成 Nodespawn可直接使用的{ command, args, shell: false }结构。在 Windows 上createSpawnCommand会基于PATH与PATHEXT解析命令真实路径若解析结果不是.cmd/.bat结尾的 shim则直接以解析出的可执行文件路径执行shell: false若是 shim则退化为用cmd.exe /d /s /c shim路径 args...启动但依然shell: false无论哪种情况都刻意避免进入 shell 模式防止引号与元字符被二次解析。问题出在测试断言本身部分createSpawnCommand的期望值假设了主机上没有全局安装typescript-language-server。一旦运行环境如 CI 的 Windows runner或开发机通过PATH暴露了全局安装的typescript-language-server.CMD解析结果就会从按原命令执行变成走 cmd shim 分支断言随之失败。这正是ambient executable lookup环境可执行文件查找泄漏——测试结果被宿主 PATH 的内容左右。以 packages/lsp-tools-mcp/test/process.test.ts 中的用例为例修复后的测试显式传入受控的PATH/PATHEXT环境使解析行为完全确定// 无 shim 可命中时直接执行不进入 shell 模式 const prepared createSpawnCommand([typescript-language-server, --stdio], win32, cmd.exe, { PATH: , PATHEXT: .COM;.EXE;.BAT;.CMD, }); // { command: typescript-language-server, args: [--stdio], shell: false } // 命中了 PATH 中的 .cmd shim退化为 cmd.exe /d /s /c shim const prepared createSpawnCommand([typescript-language-server, --stdio], win32, cmd.exe, { PATH: binaryDirectory, // 临时目录只含测试自己创建的 shim PATHEXT: .cmd;.exe, }); // { command: cmd.exe, args: [/d, /s, /c, shimPath, --stdio], shell: false }测试还覆盖了一个易踩的边界当 PATH 中同时存在无扩展名脚本如jdtls与.bat包装器时解析必须优先选择包装器见resolveWindowsCommand中 packages/lsp-core/src/lsp/process.ts 的扩展名遍历顺序这类细节正是 Windows CI 与本地开发机行为不一致的高发区。3.2 cwd/home 配置泄漏MCPstatus请求吃到了真实环境第二个根因在 MCPstatus请求上。status工具会读取真实的工作目录与主目录下的 LSP 配置用户配置、项目配置等。修复前相关测试直接继承了进程的真实cwd与 home 配置一旦本机/runner 上存在复杂的 LSP 配置status的处理时间就会在并发负载下越过 Vitest 默认的五秒超时——这是典型的ambient cwd/home configuration环境工作目录/主目录配置泄漏。修复手段是把每次请求的上下文完全收进临时目录。参考 packages/lsp-tools-mcp/test/mcp.test.ts 中的createIsolatedRequestContextfunction createIsolatedRequestContext(): LspRequestContext { const directory mkdtempSync(join(tmpdir(), lsp-mcp-status-)); tempDirectories.push(directory); return createStandaloneMcpRequestContext({ cwd: directory, homeDir: directory, env: { HOME: directory, USERPROFILE: directory, // Windows 路径下同样需要隔离 }, }); }afterEach中统一rmSync(directory, { recursive: true, force: true })清理临时目录保证测试之间、测试与真实用户环境之间互不污染。install_decision路由相关的用例则通过LSP_TOOLS_MCP_INSTALL_DECISIONS、LSP_TOOLS_MCP_USER_CONFIG、LSP_TOOLS_MCP_PROJECT_CONFIG三个环境变量把决策存储与配置路径也钉死在临时目录中packages/lsp-tools-mcp/test/mcp.test.ts。至此导致 Windows 作业失败的两类环境输入——ambient executable lookup 与 ambient cwd/home configuration——都被从测试中移除测试结果只取决于测试自身构造的输入。四、修复验证确定性指标修复后的包级验证结果记录在 .omo/evidence/20260814-pr6611-windows-codex-ci/verification.txt 与 .omo/evidence/20260814-pr6611-windows-codex-ci/qa-summary.md 中验证维度命令结果包测试npm --prefix packages/lsp-tools-mcp test25 个测试文件、96 通过 / 1 跳过 / 0 失败exit 0类型门禁npm --prefix packages/lsp-tools-mcp run typechecktsc --noEmit通过静态检查npx biome check test/process.test.ts test/mcp.test.ts test/client-wrapper.test.ts通过全量复现bun run test:codex原失败阶段通过后续 21 个安装器测试在 OneDrive Windows 工作区超时1244.32s不作为干净门禁注意对全量门禁的诚实处理由于 OneDrive Windows 工作区上 21 个后续安装器测试超时本地全量跑并不算完全干净因此以 GitHub 重新运行的 Windows 作业作为权威的全量验证。这种明确标注环境限制、不把局部结果夸大为全量通过的表述本身就是高质量 QA 证据的样本。五、真实 Codex 端到端验证codex-qa mock 模型单元测试之外QA 还驱动了一次真实的 Codex app-server 会话使用本地插件、隔离的CODEX_HOME以及 codex-qa 本地 mock 模型。关键观测点assistant 文本Hello from the codex-qa mock model.证明插件到 app-server 的消息链路打通完整执行的插件钩子sessionStart、userPromptSubmit、stop真实~/.codex/config.toml未被改动real_config_unchangedtrue隔离主目录/tmp/cqa-home.TU2Z02/codexQA 结束后隔离目录被清理sandbox_removedtrue。这条链路验证的是修复没有破坏生产行为虽然补丁只改测试但被隔离的测试依赖的createSpawnCommand等运行时逻辑仍然要在真实 Codex 进程中工作——mock 模型 隔离 CODEX_HOME 的组合在不动用真实 API 凭据的前提下完整覆盖了插件安装、会话启动、消息提交、钩子触发与目录清理。六、什么被刻意省略了QA 记录同样明确了证据边界原始 npm 安装日志、环境变量全量转储、app-server 通知流没有被复制进仓库因为它们可能包含机器本地路径与敏感环境细节。另外两次失败的 QA 启动尝试只做了摘要WSL 无法在 Windows 挂载点上对 npm shim 执行chmod首个原生流包装器无法解析 Codex 的.cmdshim。这两次尝试都没有触及任何产品断言因此不构成回归证据。这种记录失败尝试、说明省略原因的做法避免了把环境噪音误当问题证据也让后续维护者知道哪些路已经探过。七、经验沉淀跨平台 MCP 测试的确定性守则从这次修复中可以提炼出对lsp-tools-mcp及同类的 mcp-client-core、mcp-stdio-core 等 MCP 相关包普遍适用的三条守则所有 spawn 相关断言必须显式传入受控环境。默认参数env process.env会让测试继承宿主PATH/PATHEXT/ComSpecWindows 下尤其容易触发.cmdshim 分支差异测试应像 process.test.ts 那样把PATH钉死为临时目录。一切与配置读取相关的请求都要用临时 cwd/home。MCP 工具的status、diagnostics等会读真实配置的请求必须通过 request-context 注入cwd/homeDir/HOME/USERPROFILE否则测试结果随机器配置漂移。平台差异要同时覆盖解析逻辑与进程行为。createSpawnCommand的解析分支普通命令 vs shim vs PATH 命中需要单测覆盖进程树终止等平台行为则用it.skipIf(process.platform win32)显式标注不可测平台Windows 下走taskkill /t的进程树击杀见 packages/lsp-core/src/lsp/process.ts避免在错误的平台上假装覆盖。PR 6611 的这次修复规模很小——只改测试、不改生产逻辑——但恰好命中了 Windows CI 与本地开发环境之间最隐蔽的两个差异点。对于任何需要在 Windows runner 上保持稳定的 Node/MCP 项目把环境输入显式化作为测试基线是成本最低、收益最直接的一步。【免费下载链接】oh-my-openagentOmO: Just type mass ulw keyword with your prompt. Now you are the master of graph engineering.项目地址: https://gitcode.com/gh_mirrors/oh/oh-my-openagent创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考
分享:

看完干货,该让你的企业上线了

免费需求沟通 · 48 小时内出具建站方案 · 河南本地可上门