你正在用 Codex 做一个重构任务。Agent 跑了 15 分钟,修改了 23 个文件。你想看看它是怎么一步步推演到最终方案的,于是你开始往上滚。滚了 800 行。又滚了 300 行。10 分钟后你终于找到了那个关键的决策点,然后你意识到:如果你在这个节点选择了另一个方向,整棵决策树都会不一样。

但 Codex 的界面只是一个文本框。你的所有对话历史,包括提示词、工具调用、思考链、错误重试、分支探索,全部压平成了一条线。你没有空间导航,只有时间回溯。

这是 Jules Storer 对现状的不满。Storer 这个名字你不一定熟悉,但他写过的东西你大概率用过:JUCE,那个支撑了无数音频软件(从 Ableton Live 到 Teenage Engineering 的硬件)的 C++ 框架。他就是那个把"音频 GUI 很难做"这件事彻底解决掉的人。

现在,他把目光投向了另一个「交互做得很差」的领域:AI 编程 Agent。

他刚刚发布了 Juggler,一个开源的 GUI AI 编程 Agent。上线没几天就在 Hacker News 拿了 272 个投票。它不仅支持 Codex,还支持 Claude Code、Gemini、Ollama 等几乎所有主流模型。但真正有趣的地方不在于它支持什么模型,而在于它从根本上重新想象了人和 AI 协作编程的方式。

核心命题:会话不应该是聊天记录#

Juggler 有一个非常清晰的核心设计主张:AI 编程会话的本质是树,不是线。

你仔细想想这个论断。当你让 Agent 做一个复杂任务时,它在内部不断产生分支:尝试方案 A 失败、回溯、换方案 B、同时探索 C、发现 C 更好、继续深入。这是一个不断分叉、回溯、再分叉的过程。

但几乎所有编程 Agent 的界面,不管是 Codex、Claude Code 还是 Cursor,给你的都是一个线性聊天框。把你的滚动条想象成一条时间轴,你只能单向回溯。看到第 347 步做的一个糟糕决策?抱歉,你没法在那个节点「重新来过」。

Juggler 的做法完全不同。它把整个会话组织成一棵可编辑的树。任何对话节点都可以分叉出一个子线程,子线程又可以继续分叉。你可以在不同的分支之间跳转、比较、编辑。这不是「撤销」,这是「平行宇宙」。

用 Storer 自己的话说:“It’s a Yjs document, not a transcript.”

Miller Column:Finder 式的空间导航#

如果你用过 macOS 的 Finder 列视图,你对 Juggler 的界面会有一种天然的熟悉感。它使用 Miller Column 布局:根节点在最左边,选中项展开成子节点向右排列。

在代码 Agent 的场景里,这意味着:

  • 最左边是你发出的初始任务
  • 向右展开的是 Agent 的思考链
  • 再向右是具体的工具调用
  • 工具调用的返回结果继续向右展开
  • 任何时候你都可以点击回到某个中间节点,从那里重新开始

这是一种空间导航,而不是时间回溯。你不是在"回到过去的某个时刻",你是在一棵树里移动到另一个位置。这两种心智模型的差异非常大。

空间导航的好处在于,你可以同时看到多个维度的信息:Agent 的推理路径、工具调用链、文件变更、各个分支的对比。而线性聊天框只能让你在单一维度上滚动。

一切都是插件#

Juggler 的另一个核心理念是极度开放。代码的核心只是一个文档管理和编排引擎,几乎所有实际功能都由 JavaScript 扩展定义:

  • Context itemsread-filereplace-textbash 这些基础工具都是插件。每个插件自己定义如何跟 LLM 交互、如何在 UI 中呈现
  • Strategies:高层的 LLM 循环策略,比如 planresearch、或者你自己发明的任何策略,同样是插件
  • Slash Commands/clear/compact 这些命令也是插件,直接操作会话文档

这意味着 Juggler 不是一个封闭的工具,而更像一个平台。如果你的编排思路需要自己的 UI、控件或可视化效果,Juggler 给你提供了这个框架。

值得注意的是,扩展 SDK 使用 Apache-2.0 许可(应用本身是 AGPLv3),意味着你可以构建闭源扩展而不受 copyleft 约束。这在开源项目中是很聪明的设计:核心开放,生态自由。

多客户端架构:桌面应用只是其中一种视图#

Juggler 看起来像一个原生桌面应用,但它的底层是一个本地 Web 服务器,托管着一个实时协作会话。桌面应用只是连接到这个服务器的一个客户端。浏览器标签页是另一个。远程机器也可以是另一个。

这意味着你可以在代码所在的服务器上启动 Juggler,然后从笔记本、手机、甚至 iPad 上连接查看同一个会话。对于需要在远程开发机上跑长时间任务然后随时监控的场景,这个设计非常实用。

技术选型也很简洁:Go 做后端,Wails 做窗口渲染,HTML/JS 做 UI,Yjs 做实时同步。没有 Electron。

Juggler vs Codex:两种范式的对照#

到这里,我们可以清晰地看到 Juggler 和 Codex 代表了两种不同的设计哲学:

维度CodexJuggler
交互介质终端(CLI)桌面 GUI
会话模型线性聊天记录可编辑树状结构
导航方式滚动 / rewindMiller Column 空间导航
扩展机制Skills + MCPJavaScript 插件全栈
架构Agent 单进程多客户端协作架构
界面框架终端Go + Wails(非 Electron)

这不是「谁更好」的问题,而是不同场景下的不同选择。Codex 的终端模型在快速命令行操作、CI/CD 自动化、轻量交互中非常高效。Juggler 的 GUI 模型在复杂任务需要多分支探索、长时间会话需要跳转回溯、或者需要可视化理解 Agent 决策链时更有优势。

真正有趣的可能性是两者互补。你可以在终端里用 Codex 快速搞定简单任务,当遇到需要深度探索的复杂问题时切换到 Juggler,利用它的树状结构和多客户端能力。这也是 Juggler 支持 Codex 作为模型后端的原因。

一个值得关注的信号#

Juggler 的出现代表了一个重要趋势:AI 编程工具的竞争正在从「模型能力」转向「交互设计」。

半年前,大家都在比谁的模型更聪明、谁的上下文窗口更大、谁的推理速度更快。但现在 GPT-5.6、Claude Opus 4.5 等顶级模型的能力已经达到了一个阶段性的高原。当模型能力趋同时,人如何与 Agent 协作就变成了下一个差异化战场。

Juggler 的答案是:把对话变成一棵树,用空间导航取代时间回溯,把工具变成可组合的插件。这个答案未必是最终答案,但它提出了一个 Codex 等现有工具还没有认真回答的问题:当 AI 已经能写出很好的代码时,我们用来指挥它的界面,为什么还停留在 1970 年代的终端范式?

参考来源Juggler GitHub | HN 讨论 | Juggler 官网