Skip to content

fix: 运行时超时 / RoleX V2初始化 / MCP-Workspace启动 修复 + extraArgs透传#572

Merged
dfwgj merged 7 commits intomainfrom
fix/runtime-timeout
Apr 12, 2026
Merged

fix: 运行时超时 / RoleX V2初始化 / MCP-Workspace启动 修复 + extraArgs透传#572
dfwgj merged 7 commits intomainfrom
fix/runtime-timeout

Conversation

@dfwgj
Copy link
Copy Markdown
Collaborator

@dfwgj dfwgj commented Apr 12, 2026

Summary

  • fix(runtime): 修复工具执行期间空闲超时误触发,导致 AI 回复被截断
    心跳定时器(interval = timeout/2,最大 2min)在工具静默期持续重置空闲计时器

  • feat(runtime): 新增 extraArgs/extraEnv 透传至 Claude Code 子进程
    解决 LiteLLM 等网关兼容性(配置 extraArgs: { betas: "claude-code-20250219" } 可关闭 fine-grained-tool-streaming)

  • fix(core): 修复 RoleX V2 初始化失败后粘性故障(Node.js < 22 / SQLite 不可用)
    ensureInitialized() 改用 try/finally,失败后清除 this.initializing 允许重试;
    SQLite 错误包装为含版本号的可读提示;organization.ts 加 try/catch

  • fix(mcp-workspace): 修复独立部署下 mcp-server.js 启动失败
    注入 createRequire/__dirname shims 解决 ESM bundle 中 pino CJS 运行时错误;
    mcp-server entry 注入 PROMPTX_NO_WORKERS=true 跳过无法解析的 pino-pretty worker

Test plan

dfwgj and others added 7 commits April 12, 2026 11:35
工具调用结束后(message_delta stop_reason=tool_use)到工具结果返回
前,SDK 完全静默,没有任何事件重置空闲计时器,导致 10 分钟后触发
"Request timeout after 600000ms",截断仍在进行中的请求。

修复:检测到工具执行开始时,启动心跳定时器(间隔 timeout/2,最多
2 分钟),持续重置空闲计时器直到 tool_result 返回。工具结果到达、
请求完成或异常清理时,心跳自动停止。

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
所有 5 个文件读取工具(read_docx、read_xlsx、read_pptx、list_xlsx_sheets、read_pdf)
均未对用户传入的路径进行边界检查,攻击者可读取工作区之外的任意本地文件。

修复方式:在每次文件访问前调用 validateFilePath(),该函数:
1. 从 ~/.promptx/workspaces.json 加载允许的根目录(无配置时回退到 process.cwd())
2. 拒绝原始路径超出边界的请求(防止路径遍历)
3. 解析符号链接后再次校验(防止符号链接逃逸攻击)

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
新增 ClaudeEffectorConfig.extraArgs 和 extraEnv 配置项,
并通过 SDKQueryLifecycle → EnvironmentContext → buildOptions 完整透传至 SDK。

主要用途:LiteLLM 等 Anthropic 格式网关不支持 fine-grained-tool-streaming beta,
导致 "Unexpected event order" 错误。用户可通过配置:
  extraArgs: { betas: "claude-code-20250219" }
覆盖默认 beta 头列表,禁用该 beta 以恢复兼容性。

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
问题:
1. ensureInitialized() 在初始化失败后,this.initializing 永远不被清除,
   导致 rejected Promise 粘连 —— 后续所有 V2 调用都返回同一个旧的失败 Promise,
   V2 在整个进程生命周期内彻底瘫痪,无法重试。
2. 当 SQLite 不可用时(Node.js < 22),错误信息不够清晰,用户无法判断原因。
3. organization.ts 的 dispatch 调用无保护,V2 初始化失败会抛出原始异常,
   用户看到的是框架级错误而非友好提示。

修复:
- ensureInitialized() 改用 try/finally,无论成功或失败都清除 this.initializing,
  确保后续调用可以重新尝试初始化
- _doInit() 捕获 SQLite 相关错误,包装为包含 Node.js 版本的可操作提示:
  "RoleX V2 需要 Node.js 22+(内置 sqlite)或 Bun 运行时。当前运行时:Node.js X.Y.Z。"
- organization.ts dispatch 调用加 try/catch,失败时返回用户友好的错误消息

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
问题:
mcp-server.js 以 ESM 格式构建,但内联了 @promptx/logger(通过 noExternal),
logger 又依赖 CJS 包 pino,导致两类运行时错误:

1. `Dynamic require of "os" is not supported`
   ESM 上下文中没有 require,pino 内部的 __require shim 直接抛错

2. `__dirname is not defined in ES module scope`
   pino 用 __dirname 定位 worker.js,ESM 上下文中同样不存在

3. `unable to determine transport target for "pino-pretty"`
   pino transport 在部署环境下找不到 pino-pretty(无 node_modules),
   worker thread 无法启动

修复:
- tsup.config.ts 拆分为两个独立 entry 配置(index + mcp-server),
  各自注入专属 banner
- 所有 entry 注入 CJS shims(createRequire / __filename / __dirname)
  解决 require 和 __dirname 缺失问题
- mcp-server entry 额外注入 PROMPTX_NO_WORKERS=true(若未设置),
  触发 logger 的同步/文件模式,完全跳过需要 worker thread 的 pino-pretty transport

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
@dfwgj dfwgj merged commit afe93c6 into main Apr 12, 2026
@dfwgj dfwgj deleted the fix/runtime-timeout branch April 12, 2026 06:23
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

1 participant