121 lines
7.9 KiB
Markdown
121 lines
7.9 KiB
Markdown
# hatty 核心特性深度调研:串口、SSH 与 Block 式交互架构
|
||
|
||
本文档记录了关于 **串口通信(Serial Port)**、**SSH 远程主机连接** 以及 **Block 式终端交互(块状卡片交互)** 的技术可行性、底层原理、业界主流实现及在 `hatty` 终端中的落地路线。
|
||
|
||
---
|
||
|
||
## 1. 串口(Serial Port)与 SSH 会话架构调研
|
||
|
||
### 1.1 核心结论
|
||
当前基于 **Node.js (Electron) + xterm.js** 的架构,不仅完全支持串口与 SSH,而且相比纯 C/Rust 原生终端,在实现复杂度、生态成熟度以及跨平台支持上具备明显优势。
|
||
|
||
`xterm.js` 本质上是**标准 ANSI/VT100 字符流渲染器**,它与底层传输媒介完全解耦,只需实现统一的 `Session` 接口,即可无缝承载多种数据流。
|
||
|
||
```
|
||
┌────────────────────────────────────────────────────────┐
|
||
│ 统一前端界面 (hatty) │
|
||
│ 多标签页 / 分屏树 / WebGL 硬件加速 / 状态栏 │
|
||
└───────────────────────────▲────────────────────────────┘
|
||
│ 统一 IPC 字符流 (data, write, resize)
|
||
┌───────────────────────────▼────────────────────────────┐
|
||
│ 会话调度抽象层 (Session Manager) │
|
||
├───────────────────┬────────────────────┬───────────────┤
|
||
│ 1. 本地 PTY 会话 │ 2. 远程 SSH 会话 │ 3. 硬件串口会话│
|
||
│ (node-pty) │ (ssh2) │ (serialport) │
|
||
└───────────────────┴────────────────────┴───────────────┘
|
||
```
|
||
|
||
### 1.2 硬件串口支持方案(Serial Port / COM / `/dev/ttyUSB*`)
|
||
- **核心依赖**:Node.js 原生模块 `serialport`(跨平台支持 Linux、macOS、Windows)。
|
||
- **关键能力**:
|
||
1. **设备自动枚举与热插拔**:调用 `SerialPort.list()` 自动枚举 `/dev/ttyUSB0`、`/dev/ttyACM0` 等设备及其硬件 VID/PID。
|
||
2. **波特率与通信参数配置**:支持常见波特率(`9600`、`115200`、`921600`、`1500000` 等)、数据位、停止位与奇偶校验。
|
||
3. **数据管道流式打通**:
|
||
- 串口接收数据直接通过 IPC 推送至 `xterm.write(data)`;
|
||
- 终端按键输入通过 `port.write(data)` 写入串口硬件。
|
||
- **应用场景**:单片机调试(STM32 / ESP32 / Arduino)、嵌入式 Linux 开发板(U-Boot 启动日志、Kernel Console)、路由器网络设备运维。
|
||
|
||
### 1.3 远程 SSH 会话支持方案
|
||
- **两种落地形式**:
|
||
- **基础命令行模式**:借助本地 PTY,直接在终端中敲入 `ssh user@host` 即可使用(当前开箱即用)。
|
||
- **集成式主机管理器(类似 Termius / Tabby)**:
|
||
- 引入 `ssh2` 纯 JS/Node 驱动库。
|
||
- **主机簿管理**:保存 IP、端口、用户名、私钥/密码、跳板机(ProxyJump)配置。
|
||
- **断线自动重连**。
|
||
- **集成 SFTP 传输**:侧边栏可视化浏览远程文件系统,支持文件直接拖拽上传/下载。
|
||
|
||
---
|
||
|
||
## 2. Block 式终端交互(块状终端)深度调研
|
||
|
||
### 2.1 传统流式终端 vs. Block 式现代终端
|
||
|
||
| 维度 | 传统流式终端 (Stream-based) | Block 式现代终端 (Block-based) |
|
||
| :--- | :--- | :--- |
|
||
| **本质模型** | 无状态的 2D 字符网格,纯文本覆盖更新 | 结构化对象列表,每个命令为一个独立封闭卡片 |
|
||
| **命令边界** | 终端不知道命令从哪一行开始、哪一行结束 | 严格识别命令起止行、输出区域与退出状态 |
|
||
| **状态感知** | 无法感知上一条命令的耗时和执行结果 | 精准显示执行耗时(如 `⏱ 120ms`)与退出码(`✔ 0` / `✘ 127`) |
|
||
| **交互能力** | 只能靠鼠标手动拖选文本,容易误选提示符 | 一键复制该命令输出、重新运行、折叠输出、AI 诊断 |
|
||
| **代表产品** | Alacritty, Kitty, GNOME Terminal | **Warp**, **Wave Terminal** |
|
||
|
||
### 2.2 核心底层技术机制
|
||
|
||
#### A. 语义转义序列(OSC 133 / FTCS 协议)
|
||
行业公认的标准协议(FinalTerm 规范,现为 iTerm2、VS Code、Warp 采纳)。通过 Shell 钩子向 PTY 输出不可见的 ANSI 控制序列标记生命周期:
|
||
- `ESC ] 133 ; A ST`:**提示符开始(Prompt Start)**
|
||
- `ESC ] 133 ; B ST`:**命令输入开始(Command Start)**
|
||
- `ESC ] 133 ; C ST`:**输出开始(Output Start / Executed)**
|
||
- `ESC ] 133 ; D [; exitcode] ST`:**输出结束(Command Finished)**,携带命令真实退出码。
|
||
|
||
#### B. Shell 钩子自动注入(Shell Hooks)
|
||
在终端启动子进程时,通过环境变量或临时脚本注入:
|
||
- **Bash**:配置 `PROMPT_COMMAND` 与 `trap ... DEBUG`。
|
||
- **Zsh**:配置 `preexec()`(捕获命令字符串)与 `precmd()`(捕获 `$?` 状态)。
|
||
- **Fish**:注册 `fish_prompt` 与 `fish_preexec` 事件。
|
||
|
||
#### C. 输入区与输出区解耦(Detached Input Editor)
|
||
- 传统终端中,输入框与文字网格混杂在一起;
|
||
- 现代 Block 终端将屏幕底部的输入框做成独立的现代富文本编辑器(支持多行缩进、鼠标定位光标、语法高亮、Tab 智能补全);
|
||
- 用户按回车后,将输入内容打包推入上方的 Block 历史卡片流中。
|
||
|
||
#### D. 全屏 TUI 程序平滑退避(Fallback)
|
||
- 当检测到进入备用屏幕序列(`\x1b[?1049h`,如运行 `vim`、`htop`、`less`)时,自动退出 Block 卡片流模式,无缝切入标准 2D 终端网格;
|
||
- 退出全屏程序时(`\x1b[?1049l`),自动切回 Block 交互。
|
||
|
||
---
|
||
|
||
## 3. 业界代表产品与技术路线
|
||
|
||
1. **Warp**(商业闭源标杆):
|
||
- 技术栈:Rust + 自研 GPU UI 渲染引擎。
|
||
- 特色:Block 块式交互开创者,卡片式展示,内置 Warp AI 可直接读取当前 Block 的错误日志进行诊断。
|
||
2. **Wave Terminal**(开源代表,Apache 2.0):
|
||
- 技术栈:**Electron + xterm.js + Go**(与 `hatty` 技术栈高度契合)。
|
||
- 特色:卡片不仅能展示命令输出,还能在 Block 内部内嵌网页渲染、Markdown 预览、代码编辑器与图像。
|
||
3. **VS Code 终端 Shell Integration**(轻量级标杆):
|
||
- 技术栈:TypeScript + xterm.js。
|
||
- 特色:轻量接入 OSC 133,在滚动条上标记红/蓝状态圆点,支持命令导航与快捷复制输出。
|
||
|
||
---
|
||
|
||
## 4. `hatty` 落地实施路线规划
|
||
|
||
### 阶段一:轻量级 Block 标记与浮动操作栏(推荐 MVP 方案)
|
||
1. 在 `pty-manager.cjs` 中为 Bash/Zsh 注入 20 行极简 Shell 钩子脚本(输出 OSC 133 信号)。
|
||
2. 在 `terminal-view.js` 中使用 `xterm.parser.registerOscHandler(133, ...)` 捕获命令起止行与退出码。
|
||
3. 当鼠标悬停在对应命令输出区域时,浮现微交互操作栏:
|
||
- 📋 **复制命令** / 📑 **只复制命令输出**
|
||
- ⏱ **命令执行耗时**(如 `142ms`)
|
||
- 🟢/🔴 **执行状态徽章**(`0` / `1`)
|
||
- 🤖 **AI 解释报错**按钮
|
||
|
||
### 阶段二:全功能卡片式 Block 与独立输入栏(进阶重构方案)
|
||
1. 界面转变为由卡片流(`div.block-card`)构成的滚动容器。
|
||
2. 底部提供常驻的独立现代输入框,具备语法高亮与多行编辑。
|
||
3. 动态检测 `Alt Screen`,在运行 `vim`/`htop` 时自适应无缝切换。
|
||
|
||
### 阶段三:多源会话管理器(串口 + SSH)
|
||
1. 抽象 `SessionManager`,提供统一的输入输出管道。
|
||
2. 接入 `serialport` 模块,新增“硬件串口调试”标签页。
|
||
3. 接入 `ssh2` 模块,新增“SSH 主机管理与 SFTP”支持。
|