English version: A Practical Ghostty-Based Terminal Stack.

基于 Ghostty 的现代 macOS 终端方案

终端不是越复杂越好。一个好用的日常终端环境,应该满足四件事:启动快、显示稳定、路径跳转顺手、常用命令可读性更好。最近我把本机终端方案整理成一套可重复安装的组合:

Ghostty + JetBrainsMono Nerd Font + zinit + Starship + zoxide + fast-syntax-highlighting + zsh-autosuggestions + fzf + Yazi + eza/ripgrep/fd/bat/btop/duf/httpie

这套方案的目标不是把 shell 配成一个大型框架,而是用少量明确的工具替换旧的 Terminal.app + Oh My Zsh + 直接 source 插件 方案,让交互体验更现代,同时保留历史命令和旧配置的可回滚性。

一张图看整体思路

flowchart LR
  A[Ghostty<br/>GPU 加速终端] --> B[JetBrainsMono Nerd Font<br/>图标与等宽字体]
  B --> C[zsh 启动]
  C --> D[zinit<br/>延迟加载插件]
  D --> E[zsh-autosuggestions<br/>历史建议]
  D --> F[fast-syntax-highlighting<br/>语法高亮]
  C --> G[zoxide<br/>智能 cd]
  C --> H[Starship<br/>跨 shell prompt]
  C --> I[现代 CLI 别名<br/>eza rg fd bat btop duf]
  C --> J[fzf<br/>快捷键与补全]
  C --> K[Yazi<br/>终端文件管理器]

设计上,我把“终端模拟器”“字体渲染”“shell 插件”“prompt”“CLI 工具”拆开处理。每一层只做自己擅长的事,不把所有能力都塞进一个庞大的 zsh 框架里。

从旧方案迁移到新方案

旧方案通常长这样:

flowchart TB
  subgraph Old[旧方案]
    O1[Terminal.app] --> O2[Oh My Zsh]
    O2 --> O3[主题]
    O2 --> O4[直接 source autosuggestions]
    O2 --> O5[直接 source syntax-highlighting]
  end

  subgraph New[新方案]
    N1[Ghostty] --> N2[轻量 zsh]
    N2 --> N3[zinit 延迟加载插件]
    N2 --> N4[Starship prompt]
    N2 --> N5[zoxide + fzf]
    N2 --> N6[现代 CLI 工具]
  end

迁移时不删除 Oh My Zsh,也不删除旧插件。更稳妥的做法是:把旧的加载行注释掉,让它们不再影响启动性能;如果需要回滚,文件和插件仍然在。

工具与插件速览

组件角色核心功能为什么选它
Ghostty终端模拟器GPU/Metal 渲染、原生 macOS 体验、配置文件驱动比系统 Terminal 更现代,配置可迁移
JetBrainsMono Nerd Font字体等宽字体、Nerd Font 图标、Powerline 符号保证 Starship、eza 等图标显示正常
zinitzsh 插件管理延迟加载、按需拉取插件、减少启动负担替代 Oh My Zsh 的重框架加载方式
zsh-autosuggestions输入建议基于历史命令给出灰色建议保留熟悉的命令补全体验
fast-syntax-highlighting语法高亮命令、参数、路径高亮比传统高亮方案更快,适合交互 shell
StarshippromptGit 状态、目录、语言版本、命令耗时跨 shell,配置集中,显示稳定
zoxide路径跳转根据访问频率智能跳目录cd 习惯获得 z 的效率
fzf模糊查找Ctrl-R 历史搜索、文件/目录模糊选择高频交互场景提速明显
Yazi终端文件管理器三栏浏览、快速预览、文件操作、退出后回到目标目录在终端里完成 Finder 和 cd 之间的高频文件浏览
ezals 替代图标、Git 状态、树状展示恢复并增强 ll/la/l/lt 等快捷命令
ripgrepgrep 替代高速全文搜索搜索代码和文本更快
fdfind 替代简洁语法、默认忽略无关目录日常查文件更顺手
batcat 替代语法高亮、分页、行号查看文件更可读
btoptop 替代进程、CPU、内存可视化交互式资源监控更直观
dufdf 替代磁盘空间表格化展示比传统 df 更易读
httpieHTTP 客户端可读的 HTTP 请求/响应日常 API 调试比 curl 更友好

常用别名设计

传统命令新工具配置意图
lseza --icons=auto --group-directories-first保持习惯,增强显示
lleza -lh --icons=auto --group-directories-first --git恢复长列表快捷键,显示 Git 状态
laeza -lah --icons=auto --group-directories-first --git显示隐藏文件
leza -1 --icons=auto --group-directories-first单列快速浏览
lteza --tree --level=2 --icons=auto --group-directories-first二级树状结构
catbat默认获得语法高亮
greprg默认高速搜索
findfd默认更简洁的文件查找
topbtop默认使用现代资源监控
dfduf默认使用易读磁盘视图
yyazi快速打开终端文件管理器
yyyazi --cwd-file 包装函数退出 Yazi 后把当前 shell 切到最后所在目录

这些别名都应该做成“命令存在才启用”。这样在一台新机器上即使某个工具暂时安装失败,shell 仍然能正常启动。

Yazi 的预览能力依赖一组小工具:ffmpegthumbnailer 用于视频缩略图,sevenzip 用于压缩包,poppler 用于 PDF,imagemagick 用于图片处理,jq 用于 JSON。把这些依赖放进安装脚本后,新机器打开 Yazi 时不会只得到一个空壳文件列表。

历史命令必须保留

迁移 shell 时最容易被忽略的是历史命令。我的做法是显式保留原有 ~/.zsh_history

export HISTFILE="${HISTFILE:-$HOME/.zsh_history}"
export HISTSIZE=100000
export SAVEHIST=100000
setopt APPEND_HISTORY
setopt EXTENDED_HISTORY
setopt INC_APPEND_HISTORY
setopt SHARE_HISTORY
setopt HIST_IGNORE_DUPS
setopt HIST_REDUCE_BLANKS
setopt HIST_VERIFY

这样打开新的 Ghostty 窗口后,原来的历史命令仍然可以被 zsh、fzf 和 zsh-autosuggestions 继续使用。

为什么不用继续堆 Oh My Zsh

Oh My Zsh 的优点是开箱即用,缺点是它经常把主题、插件、补全和框架行为绑在一起。长期使用后,启动路径会变得不透明:到底是哪段脚本慢、哪个插件影响粘贴、哪段配置覆盖了补全行为,都不容易定位。

这套新方案的思路是:

目标做法
提高启动性能用 zinit 延迟加载交互插件
保持 prompt 可维护用 Starship 统一 prompt 配置
保持历史命令继续使用 ~/.zsh_history
保留回滚能力注释旧配置,不删除旧目录
降低自动化噪声fzf 和 zinit 交互插件只在真实 TTY 中加载
提升日常命令可读性用现代 CLI 工具接管传统命令

推荐 Ghostty 主题

Ghostty 的主题名必须来自 ghostty +list-themes,否则应用会在启动时报配置错误。我的偏好顺序是:

优先级主题风格
1TokyoNight Night接近 Tokyo Night,深色、克制、适合长时间编码
2TokyoNight Storm同属 Tokyo Night 系列,对比略有差异
3Terminal Basic Dark更接近系统 Terminal 的经典深色体验

当前默认使用:

theme = "TokyoNight Night"

配置完成后一定要验证:

ghostty +validate-config --config-file="$HOME/.config/ghostty/config"

可重复执行的安装原则

这套配置适合沉淀成一个幂等脚本。脚本应该做到:

  1. 检查 macOS 与 Homebrew。
  2. 安装 Ghostty、Nerd Font、zinit、Starship、zoxide、Yazi 和现代 CLI 工具。
  3. 注释旧 Oh My Zsh 与旧插件加载行,而不是删除它们。
  4. 用 marker block 管理 ~/.zshrc,重复执行时替换块而不是追加重复配置。
  5. 写入 Ghostty、Starship 与 Yazi 配置。
  6. prime 一次 zinit 插件,让首次打开终端时不再等待克隆。
  7. 运行 zsh -n ~/.zshrcghostty +validate-config
flowchart TD
  A[运行安装脚本] --> B{Homebrew 可用?}
  B -- 否 --> C[提示先安装 Homebrew]
  B -- 是 --> D[安装 formulae 与 casks]
  D --> E[备份并更新 zshrc]
  E --> F[写入 Ghostty 配置]
  F --> G[写入 Starship 与 Yazi 配置]
  G --> H[预热 zinit 插件]
  H --> I[验证 zsh、Yazi 与 Ghostty 配置]
  I --> J[打开新的 Ghostty 窗口]

这套方案的收益

最终得到的是一个更清晰的终端栈:

  • 终端显示由 Ghostty 与 Nerd Font 负责。
  • zsh 只保留必要的 shell 行为。
  • 插件由 zinit 延迟加载。
  • prompt 交给 Starship。
  • 路径跳转交给 zoxide。
  • 终端文件浏览和预览交给 Yazi。
  • 搜索、列表、查看、监控、HTTP 调试交给更现代的 CLI 工具。
  • 旧配置保留但不再参与启动。

这不是“把终端配得更花”,而是把常用交互路径拆清楚:哪里负责渲染,哪里负责补全,哪里负责搜索,哪里负责提示,哪里负责可读性。拆清楚之后,配置更容易迁移,也更容易维护。

继续阅读