feat: add JavaScript session orchestration runtime

This commit is contained in:
shiyue
2026-08-26 10:09:26 +08:00
parent 05480e511d
commit f15bc92d1e
17 changed files with 1483 additions and 5 deletions

View File

@@ -0,0 +1,68 @@
# 标准 JavaScript 会话编排实施计划
## Goal
为 cc-web 增加受控的 JavaScript 脚本编排能力:通过 MCP 创建、写入、异步启动和停止脚本,并注入 `@ccweb/session` 标准包,让脚本 Promise 化调用现有 ccweb 会话。
## Current Phase
Phase 5交付收尾
## Phases
### Phase 1需求与代码链路确认
- [x] 汇总已确认的 API、脚本生命周期、异常通知和错误协议
- [x] 使用 codebase-memory 确认现有 MCP、会话创建、消息发送和 steer 入口
- **Status:** complete
### Phase 2MCP 契约与脚本运行基础
- [x] 新增脚本 MCP 工具定义和 API manifest验收tools/list 能发现 create/write/run/get_run/stop/api 工具,工具输入 schema 和 manifest 可 JSON 序列化
- [x] 新增脚本目录、ESM 标准包注入和路径校验;验收:只能访问当前 cwd/.ccweb/scripts 下的 .js包可被裸名 import
- [x] 新增异步脚本运行注册表、日志落盘、停止和重启恢复验收runId 查询、stdout/stderr 分段读取、stop 吊销凭据、重启标记 killed
- **Status:** complete
### Phase 3会话标准包与服务端编排
- [x] 实现 Promise 化的当前会话、创建、发送、最后消息和语义分支能力;验收:每个 API 返回约定字符串/ID错误携带稳定 code/details
- [x] 接入现有 ccweb 会话状态、Codex App steer 和异常来源会话通知;验收:同对话复用 steer不重复运行同脚本异常才插入来源通知
- **Status:** complete
### Phase 4测试与回归
- [x] 编写脚本 MCP、标准包和异常通知回归测试
- [x] 运行语法检查、单元回归和项目 regression
- [x] 修复发现的问题并记录验证结果
- **Status:** complete
### Phase 5交付
- [x] 清理临时 TODO CSV 和本计划状态
- [x] 汇总变更、测试结果、风险和未覆盖边界
- **Status:** complete
## Key Questions
1. 如何在不让脚本轮询的情况下等待现有会话完成?——由服务端等待会话状态和持久化消息变化。
2. 如何让同对话消息复用现有 steer且不重复启动同一脚本——调用现有 handleMessage/steer并按来源+脚本路径拒绝并发重复运行。
3. 如何在脚本异常结束时通知来源对话,同时区分主动 stop——运行注册表记录 stopRequested只有非主动失败插入通知。
## Decisions Made
| Decision | Rationale |
|----------|-----------|
| 独立 Node 子进程运行脚本 | 隔离脚本异常并支持异步执行 |
| `.js` + `type=module`,注入 `@ccweb/session` | 保持用户示例并支持显式 ESM import/顶层 await |
| 服务端实现 Promise 等待 | 脚本不实现监听、轮询和等待封装 |
| 同对话发送复用现有 steer/插入 | 避免并行 turn 和递归死锁 |
| 运行记录和 stdout/stderr 持久化 | 支持异步 runId 查询、重启标记和长输出分段读取 |
| 主动 stop 不插入来源对话 | MCP 成功/失败结果已经是调用反馈 |
| 非正常结束插入来源对话通知 | 让启动脚本的 Agent 感知异常并继续处理 |
## Errors Encountered
| Error | Attempt | Resolution |
|-------|---------|------------|
| 用户级 planning-with-files 技能路径不存在 | 1 | 改用项目内 `.codex/skills/planning-with-files/` 版本 |
## Notes
- 不覆盖根目录已有的旧 `task_plan.md``findings.md``progress.md`,本任务使用 scoped planning 目录。
- 按已确认需求不设置运行时长、输出和并发硬上限;完整日志落盘,单次 get_run 只返回尾部或显式范围,避免无限响应。
- 脚本按受信代码执行,不伪造 JavaScript 沙箱仍限制脚本路径、MCP 凭据生命周期和运行记录归属。