Back to list
·23 min read·

从 macOS 到 Linux:我把 Omarchy 作为主力工作系统的一周

大学毕业以来这十余年,我的主力工作设备都是 macOS。但是近几年已经有了想要逃离苹果生态的想法,主要是因为现在大部分工作只需要终端和浏览器了,用不到那么好的硬件和资源,加上现在电脑也越来越贵,一个配置还不错的 MacBook 要 20000+,实在不划算。

本来已经慢慢接受和苹果生态深度绑定的命运,直到我在 X 上刷到了 Ruby on Rails 作者 @dhh 的一篇推文:Omarchy Quattro 发布了。

DHH 宣布 Omarchy Quattro 发布的推文
DHH 宣布 Omarchy Quattro 发布的推文

一个多小时的视频,我看了二十分钟,好像某个开关被打开了一样,立刻就拿了个 U 盘烧录了镜像,给我的台式机装了个双系统。

装好进入 Omarchy 那一刻,我就一个想法:「就是它了。」

激动地发了个朋友圈
激动地发了个朋友圈

Omarchy 的各种优劣势我不再赘述,我只能说我当时一整个周末都沉浸在 Omarchy 里,刚开的《魔兽世界》12.1 都突然没那么好玩了。

我是个 Linux 小白,此前接触 Linux 的经验只有折腾我的 Steam Deck,各种 Linux 发行版对我来说依然过于硬核,作为非科班的技术爱好者,我还是觉得有点可望不可即。

但 Omarchy 给我的感觉却如此亲切,用起来真的就是一个字:「爽」。

有网友说 Omarchy 不过就是又一个 Arch Linux 发行版,我没有什么发言权,也许别的 Arch Linux 用起来也十分出色,但 Omarchy 对于我此前的 macOS 来说,真就是打开了新世界的大门,原来桌面系统也可以这么开放和可定制化,还有十分养眼的 UI(这点很重要),以及非常迅速的响应和很低的资源占用。

只用了一个周末,我就决定把主力操作系统换到 Omarchy 试试。

按 DHH 自己的推荐来看,2026 款的 XPS 14 是最合适的,XPS 确实是最像 MacBook 的笔记本了,当然这也可能和他和戴尔有 PY 交易有点关系,我去京东一看,这价格已经和 M5 MacBook Pro 平起平坐了。

我和 AI 讨论了一会,最终决定 2000 多在闲鱼搞了台 ThinkPad X1c Gen 9,第一个卖家拖了一周还不发货,把我急得不行,最后直接去贩子那多掏了点钱收了一台,好在成色还不错。

收到的 ThinkPad X1 Carbon Gen 9 运行 Omarchy
收到的 ThinkPad X1 Carbon Gen 9 运行 Omarchy

截至目前我已经将 Omarchy 当作工作主力机使用一周了,四个字总结我的体验:「回不去了」。

  • 90% 的情况下都是全键盘操作(剩下 10% 都在浏览器里),系统快捷键熟悉使用后真的很爽。
  • 任何应用都是秒开秒关,爽(除了微信这个毒瘤)。
  • 平铺界面要比我想象中好用很多,更何况还支持平铺与浮动的切换。
  • 想怎么改系统直接和 Agent 说,想要什么功能了直接写个插件就行。
  • 真的十分 AI Native,有应用报错了,点击的默认选项就是直接把报错日志发给 Agent。
  • 工作区的设计也很快便接受了,目前我共有四个工作区:终端 + Herdr、浏览器、微信 + Telegram、飞书 + Thunderbird。通过快捷键切换,效率很高。

当然迁移的过程也并非一帆风顺,但作为一个新系统,我愿意陪伴 Omarchy 成长,因为我看到了它在 AI 时代的无穷潜力,虽然说不出哪里的哪个具体技术细节让我有这样的感觉,但我只作为一名普通用户来说,Omarchy 至少让我了解并愿意尝试 Linux,且尝试的结果我很满意。

AI 发展到如今阶段,我也从鄙夷 AI 文字创作(几年前确实太垃圾),到逐渐和 Agent 一起创建自己的内容编辑工作流,我越来越觉得「Agent 友好」已经成为了产品和服务的必备能力,一个链接直接扔给 Agent,不管是报错日志、技术文档还是配置脚本,它都能直接理解并处理。

这也是 Omarchy 最吸引我的地方。

以往在 macOS 下,系统配置很多是封闭黑盒或散落在各种图形面板里;但在 Omarchy 下,从 Hyprland 的 Lua 窗口规则、Quickshell 顶栏的 QML 小部件,到 systemd 服务与 Shell 脚本,整个系统几乎全是一目了然的纯文本。

当系统底层足够透明开放,Agent 才能真正变成系统的「Copilot」,遇到报错直接丢给它排查,想加个窗口记忆功能直接让它写脚本。原本对小白来说望而却步的 Linux,在 Agent 的辅助下反而变成了一个任你定制的大号玩具。

回头看这十几年与苹果生态的绑定,Omarchy 让我有一种买下属于自己房子的感觉,虽然很多角落需要亲自动手收拾,但桌面窗口的每一次跳动、系统的每一项逻辑,都完完全全按照我的意愿运转。

这一周用下来,我丝毫没有怀念 macOS,反而找回了高中刚接触 Android 刷机时那种纯粹的掌控感与折腾的乐趣。


以下内容借助 AI 整理

不过,从 macOS 这种开箱即用且高度封装的商业系统,切换到完全靠自己组装打磨的 Linux 平铺桌面,迁移过程中确实踩了不少坑。

很多问题看似不起眼,但在日常高频使用中,任何一处不顺手都会演变成弃坑回滚的理由。把我这一周里踩得最痛、也是最值得分享的几个实际问题整理在下面,给同样想折腾的朋友做个参考。

跨设备搬家:Mac 自带 rsync 的空格陷阱与防翻车策略

换新电脑时,公开的代码仓库最省心,git clone 下来就能直接跑。但真正重要、也最容易出事的,往往是多年积累下来的非 Git 资产:

  • 数千篇本地 Markdown 笔记和私人知识库
  • 未发布的博客草稿与本地临时配图
  • 各项目的 AI Agent 治理上下文(.agentdocs 目录)
  • 各种没进 Git 的本地开发环境配置

把这些数据从 Mac 搬迁到 ThinkPad 时,有两处极其隐蔽的坑差点让我翻车。

1. openrsync 的路径空格截断

macOS 系统自带的 rsync 实际上是远古版本(2.6.9)的 openrsync,根本不支持现代 rsync 的 --protect-args 参数。

如果同步的文件路径中带有空格(比如包含空格的项目名或目录),在 Mac 终端直接传参时,路径会被空格硬生生截断,导致传输直接报错甚至传错目录。

稳妥的做法是在 Mac 端调用时,对目标路径做显式的双重转义,并在远端先用 install -d 把目录建好:

host="user@thinkpad-tailscale-ip"
source="$HOME/Documents/My Project/"
target="/home/user/projects/My Project/"
remote_target="/home/user/projects/My\\ Project/"
 
ssh "$host" "install -d -m 755 -- '$target'"
rsync -avhn "$source" "$host:$remote_target"

2. 慎用 --delete,先 Dry-run 后哈希校验

跨系统同步最忌讳顺手加上 --delete。两端路径稍微对不齐,源端或目标端的数据几秒钟内就会被清空。

针对这种大批量核心资产迁移,我给自己定了两道保险:

  • 先跑 Dry-run:加上 -n 参数执行 rsync -avhn --itemize-changes,仔细扫一遍输出清单,确认每一项文件的增删都在预期内,再去掉 -n 正式搬迁。
  • 事后哈希校验(-c):搬迁完成后,追加 -c 参数跑一次校验 rsync -avhcn --itemize-changes。这能强制比对两端文件的内容 Checksum,避开因跨文件系统时间戳、元数据微小差异导致的漏传或假成功。

多端配置同步:只同步规则与策略,拒绝系统目录大杂烩

我日常在 Linux、macOS 和 Windows 之间来回切换。过去最容易犯的错误,就是把整个 ~/.config 目录或者一整个大而全的 Dotfiles 打包丢进同步盘。

跨操作系统的底层二进制路径、系统服务接口、缓存文件完全不同,直接同步整个系统配置目录,不出两天就会陷入各种冲突。

在我以终端 AI Agent(Oh My Pi,简称 omp)为主的工作流里,真正需要跨设备保持一致的,其实只有三样东西:

  1. Agent 治理规则与指令准则AGENTS.mdRULES.md
  2. 模型动态路由与 Provider 配置omp.ymlomp-models.yml
  3. 跨设备通用经验记忆与运维脚本omp-memory、状态栏监控脚本等)

因此,我单独建了一个专属目录 ~/omp-shared/ 作为多端统一的单一事实源(SSOT)。这个目录只放纯粹的文本规则、配置策略与轻量脚本,其他系统原生路径全部通过符号链接指过来。

跨设备单一事实源与同步拓扑
跨设备单一事实源与同步拓扑

在具体落地时,有两点非常关键:

  • 配置与敏感凭据物理隔离:所有的规则、模型路由、主题和脚本放在 ~/omp-shared/ 中,通过 Tailscale 内网的 Syncthing 节点实现各设备间的加密同步。而所有 API Key、私钥、订阅链接坚决不进同步目录,全部留在本地私有配置中(如 ~/.omp/agent/config.yml~/.config/mihomo/)。
  • 软链接安全挂载:各设备本地的工具路径不存独立副本,统一软链到共享源:
ln -s "$HOME/omp-shared/AGENTS.md" "$HOME/.omp/agent/AGENTS.md"
ln -s "$HOME/omp-shared/RULES.md" "$HOME/.omp/agent/RULES.md"
ln -s "$HOME/omp-shared/omp-memory" "$HOME/.omp/agent/memory"

同时在云端 VPS 上部署自托管的 Hindsight 长期记忆服务,通过 Tailscale 内网通信,让 ThinkPad 和 Mac 上的 Agent 随时共享同一个长期记忆库。

网络代理注入:终端 export 为什么对桌面应用无效

在 Omarchy 下,我的代理方案选择 mihoro CLI 搭配官方顶栏插件 huacnlee/omarchy-mihoro。配置网络时踩了两个坑:

第一是模式选择。在 Linux/Wayland 环境下,全局 TUN 模式很容易引起虚拟网卡冲突、DNS 泄露,甚至导致某些 Electron 应用网络异常。实测下来,直接使用 Mihoro 的本地 Mixed 端口代理(默认 7890)最省心,网络控制权清晰明了。

第二是环境变量的作用域问题。很多刚接触 Linux 的朋友在终端执行 eval "$(mihoro proxy export)" 后,发现命令行 curl 都能走代理,但从桌面启动器或菜单点开的浏览器、飞书、Thunderbird 依然打不开网页。

这是因为终端里 export 的环境变量只作用于当前 Shell 及其子进程,桌面环境唤起的图形应用压根读不到终端里的变量。

解决办法是在 Hyprland 的顶层配置(~/.config/hypr/hyprland.lua)中,直接注入全局环境变量:

-- Mihomo 系统代理:为桌面 GUI 应用统一注入代理
hl.env("http_proxy", "http://127.0.0.1:7890")
hl.env("https_proxy", "http://127.0.0.1:7890")
hl.env("HTTP_PROXY", "http://127.0.0.1:7890")
hl.env("HTTPS_PROXY", "http://127.0.0.1:7890")
hl.env("no_proxy", "localhost,127.0.0.1,::1,100.64.0.0/10")
hl.env("NO_PROXY", "localhost,127.0.0.1,::1,100.64.0.0/10")
 
-- 让 Omarchy 菜单启动的 OMP 统一继承共享配置
hl.env("PI_CONFIG_FILES", os.getenv("HOME") .. "/omp-shared/omp.yml")

配置之后,所有从图形界面启动的应用都会默认走代理,桌面菜单直接唤起的 OMP Agent 也能正确加载共享的模型配置。至于节点的订阅链接和私钥,依然遵循本地化原则,直接通过 mihoro init 在本地机器生成,不参与跨设备同步。

窗口治理:微信弹窗防挤乱与竖屏移动端小窗

平铺窗口管理器用起来非常爽快,但如果所有窗口都不加区分地强行平铺,遇到多任务或者弹窗场景就会变成灾难。

1. 微信弹窗与主界面分流

日常工作少不了微信。微信的主聊天窗口非常适合固定平铺在工作区,但要是临时弹出的图片预览、文件传输或者设置弹窗也被强行平铺,屏幕瞬间就会被切得稀碎。

hyprland.lua 中可以通过窗口 class 与 title 精确分流,让弹窗默认浮动,主聊天窗口平铺:

-- 微信窗口规则:弹窗默认浮动,主窗口平铺在 Workspace 3
o.window("(wechat|wechat-universal)", { float = true })
o.window({ class = "(wechat|wechat-universal)", title = "^(微信|WeChat)$" }, { tile = true, workspace = "3" })

2. 移动端社交小窗(460×840)

像小红书、微博、X 这类以流式图文为主的网页,在 27 寸大显示屏上全屏平铺非常浪费。我把它们统一匹配为类似手机竖屏的 460×840 浮动比例:

local mobile_social_class = "(chrome-m.weibo.cn__-Default|chrome-www.xiaohongshu.com__-Default|chrome-x.com__-Default|.*xiaohongshu.*|.*weibo.*)"
o.window(mobile_social_class, { float = true })
o.window(mobile_social_class, { size = { 460, 840 } })

3. 浮动窗口位置与尺寸记忆

原生 Hyprland 在每次重新打开浮动窗口时都会居中展示。但我习惯让小红书或 X 每次点开都乖乖停在屏幕右侧。

为此我写了一个小脚本 omarchy-window-geometry-persist.py 常驻后台,监听 Hyprland 的 IPC 事件。只要浮动小窗关闭,就记下它当前的坐标与宽高;下次再次启动,自动恢复到上次摆放的位置。

中文输入法避坑:Fcitx5 雾凇拼音与 Caps Lock 的正确解法

在 Linux 上配置中文输入法历来是一大痛点。不过在 Omarchy 上理顺层次之后,过程其实非常清晰。

1. 框架与词库快速就位

Omarchy 的图形会话里已经通过 systemd 默认启动了 fcitx5omarchy-fcitx5.service)。不需要额外去折腾其他输入法框架,也不用手动在环境变量里配 GTK_IM_MODULE

直接安装 fcitx5-rime 前端,并将口碑极佳的「雾凇拼音(rime-ice)」浅克隆到配置目录即可:

# 安装 rime 前端与图形配置工具
omarchy pkg add fcitx5-rime fcitx5-configtool git
 
# 浅克隆雾凇拼音配置并重启输入法服务
git clone --depth 1 https://github.com/iDvel/rime-ice.git ~/.local/share/fcitx5/rime
systemctl --user restart omarchy-fcitx5.service

后续更新词库时,使用 --ff-only 拉取更新并刷新,可以完整保留自己的输入词频与个人词库:

git -C ~/.local/share/fcitx5/rime pull --ff-only
fcitx5-remote -r

2. 搜索 Rime 的关键步骤

初次打开 fcitx5-configtool 添加 Rime 时,许多人在搜索列表里搜不到。

关键在于:点击添加输入法时,必须先取消勾选「Only Show Current Language(仅显示当前语言)」。在英文或默认系统布局下,Fcitx5 默认会隐藏中文输入方案。取消勾选后,立刻就能搜索到 Rime。

3. 解耦 Caps Lock:绕开状态机冲突

用惯了 Mac 的朋友最习惯用 Caps Lock 切换中英文。

但在 Omarchy 下,Caps Lock 默认被系统占作 Compose 键。如果强行在 XKB 层面把 Caps Lock 映射给 Fcitx5,会导致系统的大写锁定状态机与输入法内部的状态机打架,出现严重的吞字、打字时大写错乱等诡异现象。

最干净的工程解法是彻底解耦按键职责:

  1. 键盘底层把 Caps Lock 映射为 Menu 键;
  2. 写一个 toggle-rime-ascii 极简脚本,调用 fcitx5-remote 的原生接口在纯英文(ASCII)与雾凇拼音之间切换;
  3. bindings.lua 里把 Menu 键绑定到该脚本:
-- Caps Lock 不参与系统大写锁定,由脚本直接切换 Rime 中英文状态
o.bind("Menu", "切换中英文", os.getenv("HOME") .. "/.local/bin/toggle-rime-ascii")

顺带把默认截屏键换成了独立工具 omasnap,截图直接进剪贴板并支持即时涂鸦标注,习惯完全贴合在 macOS 下的操作流。

hl.unbind("PRINT")
o.bind("PRINT", "Screenshot", "omasnap")

状态栏定制:把顶栏做成 AI Token 与配额仪表盘

Omarchy 的顶栏基于 Quickshell 驱动,原生支持 QML 扩展定制。

平时写代码重度依赖各类大模型(OpenAI Codex、OpenCode、Google Antigravity 等),需要经常确认各家 Provider 的 Rate Limit 额度与重置时间。过去要么去终端里敲命令查,要么打开各家网页后台看,非常割裂。

我写了一个 Python 脚本 omp-bar.py,配合自定义的 omp.omarchy 顶栏小部件,把模型状态直接钉在顶栏上:

OMP 模型订阅配额监控面板
OMP 模型订阅配额监控面板
󰧑 99%·4h   󰚩 100%·4h   󰊭 70%·2h
  • 顶栏常驻:实时显示核心模型的剩余百分比与重置倒计时,额度告急时自动变黄、变红预警;
  • 悬停面板:鼠标悬停或点击弹出带进度条的完整面板,清晰列出 5 小时、按周、按月的多维度消耗明细;
  • 即时刷新:点击顶栏直接触发 omp usage invalidate 强制拉取最新用量。

抬头扫一眼就能对模型额度心中有数,写起代码来踏实很多。

统一视觉体验:贯穿系统与终端的 Kami 质感

除了系统逻辑和快捷键顺手,每天盯十几个小时的屏幕,界面的视觉舒适度直接决定了能不能长期用下去。

在配色上,我借鉴了 tw93 开源的 Kami 主题 的设计风格。这套色调低饱和、偏纸张质感,长时间看代码和文字眼睛不会疲劳。

Kami 主题与壁纸视觉效果
Kami 主题与壁纸视觉效果

为了让整个桌面环境没有割裂感,我把这套配色渗透到了日常最高频的几个界面中:

  • 桌面与终端:编写 ~/.config/omarchy/themes/kami/colors.toml,让顶栏、启动菜单、系统通知、锁屏界面与 Foot 终端拥有完全一致的底色和边框色;
  • 终端 Agent 输出:定制 ~/.omp/agent/themes/kami.json,让 OMP 终端 Agent 的代码输出高亮与系统主题自然融为一体;
  • 日常应用与壁纸:适配 Telegram Desktop 与移动端主题,并在共享目录中放好配套的和纸纹理专属壁纸。

所有的主题配置文件同样收拢在 ~/omp-shared/themes/ 统一管理。换到任何一台设备上,拉取共享目录后几秒钟就能还原出完全熟悉的工作环境。

折腾完这一整套,系统才真正从「能用」变成了「顺手」。每一处快捷键、每一个窗口行为、每一次配置同步,背后都是清清楚楚的纯文本和脚本,这种完全属于自己的透明掌控感,确实是闭源生态很难给予的。