- ROADMAP 修正过期限制说明,M3-A/M3-B/M4/M5 按实际完成勾选 - 新增 docs/PLAN-2026-10-21-backlog.md(W0–W5 波次计划,含核实记录)
17 KiB
17 KiB
OpenTerminal 下一轮迭代计划(v1.0.32+ 待办整理)
本计划整理自 2026-10-21 的三路代码审查(路线图梳理 / 代码缺口扫描 / 竞品对标), 所有条目均经源码逐一核实(文件:行号见各项「现状」)。本文件只是计划,不代表任何代码改动已开始。 执行时按波次进行,每个波次一个版本号;条目内的勾选框在执行阶段回填。
核实记录(2026-10-21 二轮):文档初稿写完后又逐条回源码验证,修正了 6 处凭印象写错的细节—— ①
pendingOpens在pty.ts而非 ssh.ts;② ssh2 无官方类型、项目用手写 shimssh2.d.ts且未声明forwardOut;③ 本地 PTY 路径没有 ZMODEM sentry(W2-4 需新写检测而非复用);④ 剪贴板图片落临时文件 不经过localPathGrants(它只授权对话框选中的路径);⑤ 官网 SFTP 区并无「双栏」宣传;⑥ zh-TW 「密碼」32 处 vs「口令」5 处(统一方向确认)。所有测试基建文件名(updater-fallback / settings-store / link-rules / zmodem-e2e / ssh-loopback)已确认存在。
总览
| 波次 | 主题 | 内容 | 预估工作量 |
|---|---|---|---|
| W0 | 文档债清理 | 计划 checkbox 回填、ROADMAP 过期条目 | 0.5h |
| W1 | 修复:更新器 + 发布脚本 + 预设升级 | 4 项小修,其中 2 项影响存量用户 | 1 天 |
| W2 | 捡漏功能(半成品补全) | 链接规则导入导出、命令库参数、i18n 统一、ZMODEM 提示 | 1–2 天 |
| W3 | 剪贴板与命令感知 | OSC 52、图片粘贴、OSC 133 marks、完成通知 | 2–3 天 |
| W4 | Shell 与 SSH 迁移链 | 本地 shell 配置档、ssh_config 导入、ProxyJump + 端口转发 | 3–5 天 |
| W5 | 差异化(择期) | 远程文件编辑、应用命令面板、终端内 AI 助理 | 各 2–4 天 |
| — | 需决策的取舍项 | 代码签名、多窗口、双栏 SFTP、传输暂停续传 | 见 §6 |
波次间的依赖:W3 的「完成通知」依赖同波次的 OSC 133 marks;W4 的 ProxyJump 与端口转发共用 ssh2 通道基建必须同一波次;W5 各项独立。
W0:文档债清理(无代码改动)
W0-1 回填两份 superpowers 计划的 checkbox
- 现状:
docs/superpowers/plans/2026-10-20-mode-button-double-click-sidebar.md12 个、docs/superpowers/plans/2026-10-16-theme-overhaul.md40 个- [ ]全部未勾,但对应代码、测试、 CHANGELOG 均已落地(v1.0.29 / v1.0.31)。 - 动作:逐项核对后勾上。
W0-2 修正 ROADMAP 过期陈述
- 现状:
docs/ROADMAP.md:33「SSH 面板暂不支持作为分屏参照」已过时——src/renderer/src/workspace/Workspace.tsx:880起的handleSplit已实现 SSH dockview 内分屏。 - 动作:删掉该条已知限制;顺带勾掉 M3-A / M5 已完成项的 checkbox,把 M4 真正未做的三项 (双栏 / 压缩解压 / 远程编辑)单列。
W1:修复(目标版本 v1.0.32)
W1-1 更新器周期定时器不再被高频设置写入重置
- 现状(已核实调用链):每次设置保存走
mutateSettings(settingsStore.ts:732)→applySystemSettings(:736)→updateScheduleApplier?.(system)(:575)→applyUpdateSchedule,而后者(updater.ts:533-537)无条件clearInterval+ 重建。拖 ColorPicker / 打字会把 4h 倒计时无限推迟。 - 改动:
applyUpdateSchedule记忆当前 interval 值,仅当updateCheckIntervalHours实际变化时重建定时器。 - 测试:
tests/updater-fallback.mjs已有 schedule 测试段(第 10 节,:586 起),在其内补「连续调用不改变倒计时起点」用例。
W1-2 「启动检查」中途拨开语义修正
- 现状(已核实文案):设置页开关标签为「启动时自动检查」(
src/shared/i18n/dicts/zh-CN/settings.ts:357), 但updater.ts:543-547startupArmed只在首次武装时置位——启动时关闭过该开关的用户在会话中途打开, 会在 5s 后立刻跑一次runCheck('startup'),与「启动时」的文案语义矛盾。 - 改动:启动时无论开关状态都消费
startupArmed(记录「启动检查已过」), 中途打开只影响周期定时器。
W1-3 修复 --channel-only --skip-gitea 静默上传
- 现状:
scripts/release.cjs:437-441CHANNEL_ONLY分支在SKIP_GITEA警告(:442-446)之前 return—— 两个参数同用时警告永不打印,且 channel 照样上传,与操作者预期相反。 - 改动:参数解析处直接拒绝该组合(
--channel-only的定义就是国内通道,叠加--skip-gitea无意义), 或把警告移到分支之前并显式确认。 - 测试:
release.cjs无测试基建,人工跑一次参数组合验证输出即可。
W1-4 高亮预设升级机制补全(影响存量用户,本波次重点)
- 现状(已核实判定链,settingsStore.ts:243-267):
refreshBuiltinRules只在LEGACY_BUILTIN_PATTERNS[rule.id].includes(存储pattern)成立时把规则升级到新 preset; 该表(:208-213)目前只有 perm/okstate/badstate 三条旧 pattern。追加新预设另有闸门LEGACY_BUILTIN_IDS(:215 起)的「存储集合恰好等于旧预设集」判定。结论:今后改任何预设的 pattern, 若不在改动同时把旧 pattern 登记进LEGACY_BUILTIN_PATTERNS,老用户将永远停在旧 pattern。 - 改动:把历次发布过的预设 pattern 全量补进
LEGACY_BUILTIN_PATTERNS(从 git 历史逐版本提取), 并在文档里写明「改预设 pattern 时必须同步登记旧 pattern」的规则(AGENTS.md 高亮一节)。 - 测试:
tests/settings-store.mjs表驱动补「旧版 pattern 规则 → 升级到新 pattern、保留用户颜色/启停」用例。
W2:捡漏功能(目标版本 v1.0.33)
W2-1 可点击链接规则的导入 / 导出 + profile 联动
- 现状:
src/renderer/src/settings/HighlightImportExport.tsx:44,52,155只处理highlightRules; AGENTS.md「可点击链接规则」章末明确「尚未做,属后续可加」。 - 改动:
src/shared/highlightIO.ts的信封机制扩展kind(或新建linkRulesIO.ts同构模块), UI 侧在ClickableLinkRules区块复用剪贴板 + FileReader + Blob 方案,不新增 IPC; profile 联动参考excludedByProfile的现有做法。 - 测试:
tests/link-rules.mjs补信封/合并用例。
W2-2 命令库 {{param}} 参数变量落地
- 现状(已核实执行链):
src/shared/commands.ts:11定义了params?: string[],全仓无消费代码。 命令的实际执行路径是Workspace.tsx:1215的runCommand→writeBroadcast(sid, \${cmd}\r`)(:1227) → 激活面板。参数替换应发生在runCommand入口处,替换产物继续走writeBroadcast`, 各 pane 的 line buffer 语义自然保持。 - 改动:执行命令时若含
{{name}}占位,弹参数输入(antd Modal 表单),替换后写入终端。 - 测试:替换逻辑抽纯函数 + 表驱动测试(占位符转义、未填参数、含
$字符等)。
W2-3 i18n 两个统一专项
- 现状(已核实计数):zh-TW 词典「密碼」32 处(settings.ts 26 + ssh.ts 4 + workspace.ts 2)为压倒性多数,
「口令」仅
dicts/zh-TW/ssh.ts5 处,统一为「密碼」并通读 指令/命令、伺服器/服务器、預設/默认; jadicts/ja/ssh.ts用「フォルダ」而settings.ts/terminal.ts用「フォルダー」。 - 改动:纯文案批量替换 + 通读;不动键名。
- 测试:无测试基建,四语言界面各过一遍设置页与 SSH 面板目检。
W2-4 本地终端运行 rz/sz 的用户提示
- 现状(已核实数据路径):ZMODEM sentry 只挂在 SSH 流上(
pty.ts:433-438handle.stream.on('data')→feedZmodem);本地 node-pty 会话的数据路径没有任何 chunk 检测。本地终端跑rz/sz只会静默卡住。 - 改动:在本地 PTY 数据路径加轻量 ZMODEM 头检测(只在看到
rz/sz启动帧时生效,常态零开销), 命中时在终端里输出一行醒目的不支持说明(走终端数据面,i18n 四语);不要接入完整 sentry。 - 测试:
tests/zmodem-e2e.mjs补「本地会话触发 → 提示且不进入传输态」。
W3:剪贴板与命令感知(目标版本 v1.0.34,对位「AI Agent 工作台」核心场景)
W3-1 OSC 52 远程写剪贴板
- 现状:只装了 fit/search/unicode11/webgl 四个 addon;远程 tmux/vim 复制无法直达本机剪贴板。
- 改动:
term.parser.registerOscHandler(52, ...)自实现(比引@xterm/addon-clipboard可控): base64 → UTF-8 安全解码(atob裸解中文会乱码,用 TextDecoder)→navigator.clipboard.writeText; 新增设置开关「允许远程程序写入剪贴板」(默认开,设上限如 1MB)。 - 测试:解码函数抽纯模块,表驱动测中文/emoji/base64 边界。
- 注意:新依赖规则——自实现则零依赖;若引 addon,渲染层依赖进 devDependencies。
W3-2 剪贴板图片粘贴进终端
- 场景:截图直接喂给 Claude Code / Kimi Code 这类支持贴图的 AI CLI。
- 改动:渲染层拦截粘贴(现有粘贴逻辑在
TerminalView.tsx:99-124确认弹窗与 :943-946 的 xterm paste 通道), 剪贴板为图片时经 IPC 让主进程clipboard.readImage()→ 落临时 PNG(os.tmpdir(),定期清理)→ 把路径文本写入终端。不涉及localPathGrants:该注册表只授权「系统对话框选中的路径」 (grantPickedFiles/grantPickedDirectory,localPathGrants.ts:110,119),临时文件由主进程自己写入、 应用自身不读它,无需授权。 - 测试:临时文件命名/清理逻辑的单测;实际粘贴行为列入发版手测清单。
W3-3 OSC 133 命令块感知(marks)
- 现状:
src/main/shellIntegration.ts:8,39,60已注入 OSC 7(bash/zsh/PowerShell 三个适配器)—— 扩到 133 是同一处注入脚本 + xterm 侧 mark 注册。 - 改动:注入脚本补
OSC 133;A/B/C/D(prompt start / command start / output start / finished+exitcode); 渲染层监听 mark 事件建「命令块索引」,提供:- 滚动条刻度(marks gutter)
- 快捷键跳上/下一条命令
- 「复制本次命令输出」(整块选中复制——整段取 AI agent 输出是核心诉求)
- 测试:注入脚本的字面量生成有现有测试模式可仿;mark 索引纯函数表驱动。
- 风险:OSC 133 在不同 shell/嵌套 tmux 下行为差异大,首版只承诺 bash/zsh/pwsh,tmux 内标注「依赖外层终端透传」。
W3-4 长任务完成通知(依赖 W3-3)
- 场景:多路分屏跑 AI agent,跑完切走被叫回来——本产品核心场景。
- 改动:OSC 133 D(命令结束)到达且该 pane 不可见且命令耗时 > 阈值(设置项,默认 10s)时:
托盘气泡(复用
tray.ts notifyUpdate的通道)+ 标签强调态。退出码非零时气泡文案区分成功/失败。 - 测试:判定逻辑抽纯函数(耗时阈值、可见性、退出码),表驱动。
W4:Shell 与 SSH 迁移链(目标版本 v1.0.35,获客向)
W4-1 本地 Shell 配置档
- 现状:
src/main/pty.ts:220-228win32 硬编码powershell.exe;createPty的opts.shell/opts.shellArgs已存在但无任何调用方传参——只差最后一公里。 - 改动:设置新增「默认 Shell」下拉(自动探测:
wsl.exe -l -q枚举发行版、git-bash.exe常见路径、 cmd/pwsh/powershell),Workspace.tsx的createPty()调用点传入;工作区「+ 新建终端」沿用默认, 侧栏可提供「以其它 shell 新建」次级菜单。 - 测试:探测函数接受注入的枚举源(测试缝),表驱动覆盖各解析分支;真实 WSL/Git Bash 列入手测清单。
W4-2 ~/.ssh/config 导入
- 现状:无任何 ssh_config 解析代码;国内用户从 Xshell/PuTTY 迁移时「几十台机器重录」是弃用理由之首。
- 改动:解析器抽纯模块(Host/HostName/User/Port/IdentityFile/ProxyJump,多 Host 与通配 Host
*), 映射到SshConnection并批量追加进connections.json(新增字段时同步三处:PUBLIC_KEYS/toPublic()/saveConnection()新记录字面量——AGENTS.md 明确要求)。 ProxyJump 字段在 W4-3 之前先存起来不生效。 - 测试:解析器表驱动(注释、大小写、引号、通配、Include 提示不支持)。
W4-3 SSH ProxyJump + 端口转发(同一波次,共用通道基建)
- 现状(已核实):
forwardOut|ProxyJump|jumpHost全仓零命中;企业内网 bastion 是刚需。 两个核实到的前置事实:① 飞行中连接登记表pendingOpens在src/main/pty.ts:155,329,360(不在 ssh.ts);② ssh2 不带类型定义,项目用手写 shimsrc/main/ssh2.d.ts, 其中只声明了connect(),没有forwardOut(:85-86)——必须扩 shim。 - 改动:
- 连接模型:
SshConnection增加jumpHostId(引用另一条连接)与forwards[](本地/远程/SOCKS)。 - 主进程:
ssh2先连跳板 →forwardOut建通道 → 在通道上再握手目标机;复用pendingOpens的中止与超时体系(每跳独立超时);主机指纹逐跳走现有 host key 队列。 - 类型:扩展
src/main/ssh2.d.ts补forwardOut等声明。 - 端口转发:连接建立后按
forwards[]起本地监听,断开/失败时面板给出醒目状态。
- 连接模型:
- 测试:ssh-loopback 测试基建可起两级跳板做端到端;真实服务器场景列入手测清单。
- 风险:这是本计划里架构风险最高的一项,建议单独立项评审后再动。
W5:差异化(择期,各独立立项)
W5-1 远程文件内置编辑器
- 双击 SFTP 文件 → 面板内打开编辑(轻量 textarea 起步,Monaco 体积与零依赖取向冲突需另行评估);
保存自动回写;处理编码(UTF-8 优先)、CRLF、无写权限提示。改动点:
FilePanel.tsx+sftp.ts新增 read/write 文件 IPC(走 per-op 超时bounded())。
W5-2 应用级命令面板 + 可自定义快捷键
Ctrl+Shift+P(已核实全仓无占用)动作注册表 + antd 模糊搜索 Modal;快捷键录制器复用src/shared/reservedAccelerators.ts保留键表(acceleratorParts/isReservedAccelerator,防抢 Ctrl+L/Ctrl+F)。 价值:功能密度已高,这是「后续功能不再堆 UI」的前置投资。
W5-3 终端内 AI 助理
- OpenAI 兼容端点(DeepSeek/Kimi/智谱均可接入),「
#开头自然语言 → 建议命令」, 默认只生成、回车前必须人工确认;报错解释走显式按钮。红线:任何终端内容不外发, 与现有「诊断日志不含内容」的隐私原则保持一致。 - 注意:引入网络请求路径,需过安全评审;不绑账号、无云同步(相对 Warp 的国内优势)。
§6 需决策的取舍项(不排期,等拍板)
| 项 | 取舍点 | 建议 |
|---|---|---|
| 代码签名证书 | 外部成本(~数百美元/年);无签名则 SmartScreen 拦截 + 通道完整性缺口 | 用户量到一定规模再做 |
| 多窗口 / 标签拖出 | 与单实例设计冲突,sessionState/owner 归属需重构 |
等真实多显示器用户反馈 |
| SFTP 本地↔远程双栏 | 大工程(本地文件树模型 + 传输层重做);官网 SFTP 区从未宣传「双栏」(i18n fs.* 文案只讲远程面板 + 上传下载),无宣传口径包袱 | 观望;拖拽上传先满足大半诉求 |
| 传输暂停/续传 | TransferState 无 paused 态,需断点续传协议层 |
观望 |
| 性能优化第二阶段(B3/B4) | 项目自定规则:没拿到真实 PERF 日志前不许凭感觉动 | 维持观测,等数据 |
xterm 解 pin 回 ^ |
锁 6.1.0-beta.304 因 IME 修复;解 pin 需同步 addon-unicode11 peer 并重测中文输入法 |
等上游 6.1.0 stable |
| autoWrap=false 固定列宽 | xterm 无原生支持,等于自写列裁剪层 | 不做 |
执行约束(所有波次通用,摘自 AGENTS.md 铁律)
- 新增纯逻辑一律抽零 import 纯模块 + Node 原生类型剥离表驱动测试,测试数随 AGENTS.md 清单同步更新
- 依赖分类:
src/main|preload实际 import 的才进 dependencies;渲染层一律 devDependencies - i18n 四语言键必须同步(zh-CN/zh-TW/en/ja),缺键回落简中但属必须修
- 新增「渲染层构造本地路径传主进程」的调用点必须过
localPathGrants - CSS 一律
var(--ot-*),新代码禁止裸颜色字面量(tests/css-theme-vars.mjs守门) - 每个发版 commit 必须带
package-lock.json;发布流程照 AGENTS.md「发布新版本」六步 - 改 AGENTS.md 已文档化的行为时,同步更新 AGENTS.md