pi-tmux-fork

Pi extension that forks the current session into a tmux pane/window, inheriting the full conversation history and reusing the parent session's prompt cache. Adds git worktree isolation for child agents.

Packages

Package details

extension

Install pi-tmux-fork from npm and Pi will load the resources declared by the package manifest.

$ pi install npm:pi-tmux-fork
Package
pi-tmux-fork
Version
0.2.3
Published
Jul 30, 2026
Downloads
466/mo · 28/wk
Author
geeyu
License
MIT
Types
extension
Size
42.2 KB
Dependencies
0 dependencies · 1 peer
Pi manifest JSON
{
  "extensions": [
    "./"
  ]
}

Security note

Pi packages can execute code and influence agent behavior. Review the source before installing third-party packages.

README

pi-tmux-fork

npm version npm downloads license GitHub

pi 扩展,在 tmux 中 fork 当前会话,让子会话继承完整的对话历史,并复用父会话已建立的 prompt 缓存,避免重复 prefill。

安装

pi install npm:pi-tmux-fork
# 或从 GitHub 安装:
pi install git:github.com/geeyu/tmux-fork

安装后无需额外配置,重启 pi 即可在 tmux 会话内使用 /tmux-fork* 命令。

特性

  • 会话 fork: 完整复制父会话的 system prompt 与历史轮次,发送给 LLM 的 prompt 前缀字节级一致。
  • 缓存复用: 对于 GLM-5.2 等隐式缓存模型,子会话能直接命中父会话的 prompt 缓存,省去重复 prefill 计费(实测命中率从 0.4% 提升到 95%)。
  • worktree 隔离: /tmux-fork-gt 在独立的 git worktree 中打开子 agent,文件改动互不干扰,同时通过 cwd-cache-fixer 保留缓存。
  • 安全清理: /tmux-fork-gt-clean 交互式列出并删除 worktree,自动检测进程占用,避免误删正在使用的目录。

前置要求

  • 已安装 pi,且 pi 命令在 PATH 中。
  • 运行在 tmux 会话内(环境变量 TMUX 存在)。
  • 当前会话已持久化(非 ephemeral 临时会话),否则没有可 fork 的 session 文件。
  • /tmux-fork-gt 还要求当前目录位于某个 git 仓库内。

命令

/tmux-fork

fork 当前会话,在 tmux 新窗口或分屏中打开一个全新的 pi 子会话。子会话继承全部对话历史,prompt 前缀与父会话一致以复用缓存。

/tmux-fork

无需参数。执行后会根据配置选择「整页新窗口」或「当前窗口分屏」打开子会话。

缓存接力: 若当前会话本身是 /tmux-fork-gt 的后代(worktree 会话),/tmux-fork 会把 PI_CACHE_CWDcwd-cache-fixer 扩展接力给孙会话,使其 system prompt 中的 cwd 仍固定为原仓库根,保持缓存一致。孙会话仍在同一 worktree 中操作,隔离性不变。

/tmux-fork-gt

fork 当前会话,并在独立的 git worktree 中启动子 agent。子 agent 的文件操作只影响 worktree,与主工作区隔离;同时通过 cwd-cache-fixer 扩展把 system prompt 中的 cwd 固定为原仓库根,保留 prompt 缓存。

/tmux-fork-gt <简要任务描述>
参数 说明
<简要任务描述> 任务的一句话描述,会作为子 agent 的首条用户消息传入,必填

示例:

/tmux-fork-gt 把登录页的表单校验抽成独立组件

执行流程:

  1. 解析 git 根目录,计算下一个 worktree 编号(gittree-<N>-task)。
  2. 确保 .worktrees/ 已被 .gitignore 忽略。
  3. .worktrees/gittree-<N>-task 创建 git worktree(编号冲突时自动递增重试)。
  4. patch session 文件首行的 cwd 字段指向 worktree。
  5. 在 worktree 中启动 pi,注入 PI_CACHE_CWD 环境变量。

并发 fork 时多个引导脚本可能算出相同编号,会逐个递增重试,直到 git worktree add -b 成功。

/tmux-fork-gt-clean

列出并清理 /tmux-fork-gt 创建的 gittree worktree。支持三种用法:

/tmux-fork-gt-clean             # 弹窗选择要删除的 worktree
/tmux-fork-gt-clean all         # 清理全部空闲 worktree(跳过 in-use)
/tmux-fork-gt-clean <name>      # 直接清理指定名称,跳过弹窗
参数 说明
all 批量清理所有空闲 worktree,被进程占用的会跳过
<name> worktree 名称(gittree-<name>-task 中的 name 部分),不区分大小写

安全机制:

  • 通过 lsof 检测进程占用(cwd 在该 worktree 下的 pi / node / bash 进程),标记为 in use
  • in use 的 worktree 会被拦截,不会删除。
  • 删除前会二次确认(弹窗或 ctx.ui.confirm)。
  • 清理后自动执行 git worktree prune

子 agent 限制: /tmux-fork-gt/tmux-fork-gt-clean 在 fork-gt 出来的子 agent(worktree 会话)里不注册,命令列表中不可见。子 agent 再开 worktree 会嵌套混乱,且 clean 按 git root 扫描所有 .worktrees/gittree-*,可能误删兄弟或父会话的 worktree。/tmux-fork(普通 fork,不开 worktree)不受影响,仍可在子 agent 中使用。

配置

~/.pi/agent/settings.json 中添加 tmuxFork 字段:

{
  "tmuxFork": {
    "mode": "new-window",
    "closeOnExit": false
  }
}
字段 类型 默认值 说明
mode "new-window" | "split-window" "new-window" 打开方式。new-window 整页新窗口;split-window 在当前窗口分屏(仅一个 pane 时右侧水平分屏,多个 pane 时在最后一个 pane 下方垂直分屏)
closeOnExit boolean false pi 退出后是否关闭 tmux 窗口。true 直接关闭;false 保留 shell,方便查看输出

未配置时使用默认值。

工作原理

缓存复用

fork 时调用 SessionManager.forkFrom(src, cwd),创建一个新的 session 文件,复制父会话全部非 header 条目,并写入新 header(parentSession 指向源文件)。由于发送给 LLM 的 prompt 前缀(system prompt + 历史轮次)字节级一致,隐式缓存模型能直接命中父会话已建立的缓存。

worktree 场景下的缓存修复

/tmux-fork-gt 会把子 agent 的 cwd 切换到 worktree 路径。pi 的 system prompt 末尾会写入 Current working directory: <cwd>,而隐式缓存按 prompt 前缀逐 token 匹配——cwd 变化会导致末尾这行及其后的全部对话历史缓存未命中。

解决方式由 cwd-cache-fixer.ts 扩展完成:在 before_agent_start 事件中,把 system prompt 中的 cwd 字符串替换回原仓库根(由 gittree-bootstrap.mjs 通过 PI_CACHE_CWD 环境变量注入)。仅影响发送给模型的字符串,bash 与文件工具的真实执行 cwd 仍是 worktree,隔离性完全保留。

未设置 PI_CACHE_CWD 时,cwd-cache-fixer 不注册任何处理逻辑,零开销。

文件说明

文件 说明
index.ts 扩展入口,注册三个 /tmux-fork* 命令
gittree-bootstrap.mjs gittree worktree 创建与 pi 启动引导脚本,由 /tmux-fork-gt 调用
cwd-cache-fixer.ts worktree 场景下修复 prompt 缓存命中率的扩展,由 bootstrap 注入

常见问题

提示 Not inside tmux.

当前不在 tmux 会话内。请先 tmuxtmux a 进入会话再执行命令。

提示 No session file (ephemeral).

当前会话是临时会话,没有持久化的 session 文件,无法 fork。请使用持久化会话。

/tmux-fork-gt 提示 Usage: /tmux-fork-gt <brief task description>

缺少任务描述参数。该命令需要一句话描述要执行的任务,例如:

/tmux-fork-gt 修复用户列表分页 bug

/tmux-fork-gtgit rev-parse --show-toplevel 失败

当前目录不在 git 仓库内。该命令要求 cwd 位于某个 git 仓库中。

清理时提示 is in use, cannot remove.

该 worktree 下有进程正在运行(pi / node / bash)。请先关闭对应进程后再清理,或直接删除其他空闲的 worktree。

这是预期行为。pi 退出后会保留 shell,方便查看输出。若希望 pi 退出即关闭窗口,把 closeOnExit 设为 true

fork-gt 出的子 agent 里找不到 /tmux-fork-gt

这是预期行为。worktree 子 agent 会话中 /tmux-fork-gt/tmux-fork-gt-clean 被禁用(不注册),避免嵌套 fork 造成混乱或误删兄弟 worktree。子 agent 里仍可用 /tmux-fork(普通 fork)。