Files
terminal-lab/wetty/xterminal-wetty-diff.md
2026-03-03 16:07:18 +08:00

10 KiB
Raw Permalink Blame History

xterminal 与 wetty client 详细差异对比

1. 对比范围与结论

本文对比对象:

  • xterminal/Users/gavin/lab/xterminal
  • wetty 当前项目前端 client/Users/gavin/lab/wetty/src/client/wetty/**(以及其页面与配置面板)

核心结论:

  1. 两者不是同层替代关系。xterminal 是前端终端组件库,wetty client 是完整 Web SSH 网关客户端。
  2. wetty client 的核心能力来自 xterm.js 真终端仿真;xterminal 核心是“CLI 交互组件”,终端协议能力主要由业务层补齐。
  3. 若目标是“做 SSH/PTY 级别会话”,wetty client 路线更直接;若目标是“嵌入式 Web CLI 组件”,xterminal 更轻更可控。

2. 产品定位与边界

xterminal组件库定位

  • 对外是 XTerminal 类 APImount/write/history/setCompleter/pause/resume/dispose)。
  • 不绑定任何固定后端协议,网络连接由业务方自行实现。
  • 证据:
    • source/index.ts:14(类定义)
    • source/index.ts:95(挂载)
    • source/index.ts:53(输出 API
    • source/index.ts:90(补全)

wetty client业务客户端定位

  • 页面入口直接完成:终端初始化、断线重连 UI、网关连接、数据收发。
  • 与运行配置、网关协议、页面 DOM 强耦合。
  • 证据:
    • src/client/wetty.ts:26(启动终端)
    • src/client/wetty.ts:38socket 事件链)
    • src/client/wetty/socket.ts:43(网关 socket 实现)

3. 渲染与终端仿真能力

wetty clientxterm.js 终端仿真

  • 直接继承 @xterm/xtermTerminal
  • 加载了 FitAddonWebLinksAddonImageAddon
  • 原生具备终端仿真语义(光标、控制序列、窗口 resize、链接识别等
  • 证据:
    • src/client/wetty/term.ts:13
    • src/client/wetty/term.ts:21
    • src/client/wetty/term.ts:23
    • src/client/wetty/term.ts:24

xterminal组件渲染模型

  • 输出层以 HTML 片段写入为主。
  • 核心库不自带完整 VT/ANSI 终端协议仿真。
  • ANSI 处理与网关协议示例主要存在于 demo 脚本,不在库核心 API。
  • 证据:
    • source/output/index.ts:40
    • source/output/index.ts:49
    • demo/main.js:381ANSI 转换)

4. 输入模型差异(交互体验关键)

wetty client按键流streaming input

  • 用户每次按键通过 term.onData 立即发送到后端。
  • 更接近真实 SSH TTY 行为(如逐字符编辑、交互式全屏程序)。
  • 证据:
    • src/client/wetty.ts:60

xterminal行输入line-based

  • 默认在 Enter 时触发 data 事件并提交一整行。
  • 上下箭头与历史命令是组件内建行为。
  • 证据:
    • source/instance.ts:136Enter 分支)
    • source/instance.ts:141emit data
    • source/instance.ts:147(历史导航)

影响:

  1. 需要 PTY 级“实时按键”时,xterminal 必须由业务层额外桥接按键事件。
  2. 需要“类 REPL 文本命令输入”时,xterminal 默认体验更简单。

5. 协议与连接层

wetty client内置网关协议适配

  • 内建 GatewaySocket,封装事件 connect/login/data/logout/disconnect/error
  • 支持 init/stdin/resize/control 帧。
  • 自动处理 ping/pongconnecteddisconnect 控制帧。
  • 证据:
    • src/client/wetty/socket.ts:3
    • src/client/wetty/socket.ts:57
    • src/client/wetty/socket.ts:103
    • src/client/wetty/socket.ts:238

xterminal协议在业务层demo实现

  • 核心库无 WebSocket 协议绑定。
  • demo 中手工实现网关连接、帧发送、回包处理、排队与批量 flush。
  • 证据:
    • demo/main.js:635connectByConfig
    • demo/main.js:572handleGatewayFrame
    • demo/main.js:501stdin 发送)

6. 配置系统与可配置能力

wetty client

  • 运行时读取 /terminal.config.json,并做最小字段校验、选中 server 逻辑。
  • 有 iframe 配置面板,可改大量 xterm 选项并持久化 localStorage.options
  • 证据:
    • src/client/wetty/runtimeConfig.ts:77
    • src/client/wetty/runtimeConfig.ts:107
    • src/client/wetty/term/confiruragtion.ts:8
    • src/client/wetty/term/load.ts:10
    • src/assets/xterm_config/index.html:62

xterminal

  • 核心库配置简单(主要是挂载 target
  • 无内建“终端参数 GUI 编辑器”,这部分由业务层自行实现。
  • 证据:
    • source/types.d.ts:103

7. 移动端策略对比

wetty client

  • 对 xterm 屏幕加 contenteditable 以触发软键盘。
  • 页面内置功能键浮层方向键、Esc、Ctrl、Tab
  • 证据:
    • src/client/wetty/mobile.ts:3
    • index.html:28
    • src/client/wetty/term.ts:190

xterminal

  • 核心对移动端做了更系统处理:
    • 隐藏 textarea + 自绘光标
    • visualViewport 监听,动态补偿软键盘遮挡
    • 避免 iOS Safari 聚焦导致 body 整体上推
  • 证据:
    • source/instance.ts:58
    • source/renderer/index.ts:27
    • theme/index.css:68

结论:

  1. wetty 的移动端更偏“终端页面增强”。
  2. xterminal 的移动端更偏“组件内部自洽”。

8. 安全与风险点

8.1 前端渲染安全

  • xterminal 提供 writeSafe/escapeHTML,明确区分不可信文本输出路径。

  • 证据:

    • source/index.ts:61
    • source/output/index.ts:19
  • wetty 断线信息使用 innerHTML 注入文本,若消息来源不可信有注入风险。

  • 证据:

    • src/client/wetty/disconnect.ts:9

8.2 配置泄露风险

  • 两边当前 terminal.config.json 都包含明文密码,属于高风险配置习惯(即使是开发环境)。
  • 证据:
    • /Users/gavin/lab/wetty/terminal.config.json
    • /Users/gavin/lab/xterminal/terminal.config.json

9. 特性差异清单(功能维度)

wetty client 独有/更强

  1. xterm.js 终端仿真与 addon 生态。
  2. 现成文件下载控制序列解析(ESC[5i / ESC[4i)。
  3. 完整连接态 UIoverlay、reconnect、配置侧栏
  4. 网关初始化载荷构造(含证书/私钥/密码多认证类型)。

证据:

  • src/client/wetty/download.ts:4
  • src/client/wetty/download.ts:76
  • src/client/wetty/socket.ts:161
  • index.html:14

xterminal 独有/更强

  1. 组件化 API 清晰,易嵌入任意前端。
  2. 事件总线与资源释放边界明确(disposeregister)。
  3. 历史记录与补全接口简洁。
  4. 测试覆盖相对更系统input/output/history/emitter/xterminal

证据:

  • source/index.ts:117
  • source/emitter/index.ts:16
  • tests/xterminal.test.ts:4
  • tests/input.test.ts:5

10. 工程化与依赖体量

依赖与发布目标

  • wetty

    • 运行时依赖较重(含 @xterm/*expresssocket.ionode-pty 等)。
    • 发布目标是应用(bin/main + server + client
    • 证据:package.json:44dependencies
  • xterminal

    • 核心 runtime 无 dependencies仅 devDependencies
    • 发布目标是库UMD + ESM + CSS + types
    • 证据:package.json:64devDependenciesrollup.config.js:31

产物规模(当前工作区构建结果)

  • wetty client bundlebuild/client/wetty.js511K(含 source map 更大)。
  • xterminal distxterminal.esm.js8.5Kxterminal.umd.js16K

结论:

  1. 若只需要嵌入命令交互 UIxterminal 体量优势明显。
  2. 若需要终端仿真,wetty/xterm.js 的体量属于能力成本。

11. 测试对比

  • wetty 当前仓库测试集中在:

    • 客户端 FileDownloader
    • 服务端 shell escaping
    • 证据:src/client/wetty/download.spec.ts:10src/server/shared/shell.spec.ts:5
  • xterminal 测试覆盖:

    • xterminal/input/output/history/emitter/disposable/reactivity
    • 证据:/Users/gavin/lab/xterminal/tests/*.test.ts

12. 当前项目内一个关键不一致点

在当前 wetty 仓库中,前端 client 已改为“网关 WebSocket 帧协议”,但后端原有代码仍是 Socket.IO 事件模型(input/resize/commit)。

  • 前端证据:src/client/wetty/socket.ts:97
  • 后端证据:src/server/spawn.ts:38src/server/socketServer/socket.ts:38

这意味着:

  1. 当前 client 与本仓库原 server 不天然对接。
  2. client 实际更像在对接外部网关服务,而不是本地 wetty server。

13. 选型建议(按目标场景)

选 wetty client 路线

适合:

  1. 目标是“浏览器里完整 SSH 终端”。
  2. 需要 xterm.js 级别兼容能力(控制序列、终端行为一致性)。
  3. 接受更重依赖与更复杂调试链路。

选 xterminal 路线

适合:

  1. 目标是“可嵌入、可定制、轻量 CLI 组件”。
  2. 协议、渲染、会话行为希望完全可控。
  3. 可接受自行补齐 SSH/ANSI/PTY 的业务层逻辑。

14. 如果要做“xterminal + wetty 能力融合”,推荐最小改造路径

  1. 保持 xterminal 作为 UI 输入输出壳,不直接替换为 xterm.js。
  2. 单独抽出 gateway client 模块(connect/send/receive/reconnect),不要继续写在 demo/page 脚本。
  3. 定义统一帧协议适配层,把 init/stdin/resize/control/stdout/stderr/error 规范化。
  4. 将 ANSI 渲染器从 demo 抽为独立模块补测试尤其是跨帧、退格、CR/LF
  5. 最后再评估是否有必要迁移到 xterm.js仅在终端兼容性成为瓶颈时

15. 风险清单(落地前需确认)

  1. 明文密码配置必须替换(令牌化或后端临时凭据)。
  2. 断线错误信息渲染方式应改为安全文本输出(避免 innerHTML 注入)。
  3. 若要支持交互式全屏程序vim/top/tmux需确认输入模型是按键流而非行输入。
  4. 若继续沿用移动端触控条,需要统一“焦点不丢失”的处理策略(当前两项目实现不同)。

16. 快速摘要(一页版)

  1. xterminal 是“轻量终端 UI 组件库”;wetty client 是“完整 Web SSH 客户端”。
  2. wetty 的强项是 xterm.js 终端仿真;xterminal 的强项是组件化、轻量、可嵌入。
  3. 两者可融合,但不是无缝替换;最大差异在输入模型、协议耦合、终端仿真深度。
  4. 当前 wetty 仓库里 client/server 协议模型存在分叉,后续演进需先统一架构方向。