1. 先搞清楚这两个选项到底在争什么很多人第一次在 Codex 里看到Current checkout和New worktree这两个选项时手指会停在鼠标上犹豫几秒。界面上没有任何解释文档里也只是一笔带过选错了倒不会炸库但接下来半小时的操作节奏会完全不同。我自己最开始用的时候凭直觉一直选 Current checkout直到有一次同时要验证两个互斥的改动方案才被迫去研究 New worktree 到底是怎么回事。先把结论摆在前面这两个选项的本质区别是你接下来的改动落在哪个工作目录上。Current checkout 就是你现在打开的这个目录New worktree 则是基于当前仓库另开一个独立的工作目录。听起来像是复制一份代码这么简单但真正影响体验的是它们背后的 Git 机制——一个是原地修改一个是利用 Git 的 worktree 能力做隔离。为什么这个选择值得单独写一篇因为 Codex 这类工具的工作模式是你给指令它去改代码而改代码这件事一旦和 Git 的工作区状态纠缠在一起就会衍生出一堆连锁反应未提交的改动会不会被覆盖、能不能同时跑两个任务、切换分支时会不会冲突、任务做完后怎么清理。这些问题的答案全都取决于你一开始选了哪个。我见过不少人把这两个选项当成随便选一个都行的按钮结果要么是辛苦写了半天的改动被新任务冲掉要么是磁盘里堆了一堆忘记删除的临时目录。所以这篇就按我自己的使用经验把这两个选项的适用场景、底层逻辑、实操细节和踩坑记录完整梳理一遍。不管你是刚接触 Codex 的新手还是已经用了一段时间但一直没搞明白区别的老用户应该都能找到对你有用的部分。2. Current checkout 的真实工作方式与适用边界2.1 它其实就是就地开工Current checkout 的逻辑非常直白Codex 直接在你当前打开的这个仓库目录里干活。你看到的文件、你正在编辑的分支、你还没提交的改动全都在它的操作范围内。它不会给你另开一个目录也不会帮你把当前状态备份一份就是在这个已经存在的空间里继续叠加新的修改。这种模式最大的好处是零切换成本。你不需要在多个目录之间跳来跳去不需要重新配置编辑器的工作区也不需要重新装依赖如果依赖是装在项目目录里的话。任务做完改动就在你眼前直接 review、直接提交整个流程是一条直线。我日常大部分场景都用 Current checkout尤其是那种我知道要改什么、改动范围可控、做完就提交的任务。比如修一个明确的 bug、加一个小的工具函数、调整一段配置这些用 Current checkout 是最顺手的。它就像你在自己书桌上改稿子笔和纸都是现成的。2.2 什么时候它会变成麻烦Current checkout 的问题不在于它本身而在于它和你的未提交改动共享同一个空间。这是最容易被忽略的一点。假设你手头有一批改了一半的代码还没提交这时候你让 Codex 用 Current checkout 去做一个新任务。Codex 在改代码的过程中很可能会碰到你正在改的那些文件。如果它的改动和你的改动落在同一片区域冲突就来了——轻则它覆盖了你的修改重则两边的内容混在一起你分不清哪段是谁写的。我自己踩过一次比较典型的坑当时在调一个模块的日志输出改了几个文件还没提交顺手让 Codex 用 Current checkout 去加一个无关的小功能。结果它为了保持代码风格一致把我正在改的那个日志文件也顺手格式化了我半天的调整全没了。虽然能从 Git 的暂存区或者编辑器的本地历史里找回一部分但那种感觉非常糟糕。所以 Current checkout 有一条隐含的使用前提你当前的工作区最好是干净的或者至少你清楚哪些文件正在被改动并且这些文件不会和 Codex 的任务重叠。如果你做不到这一点就应该考虑 New worktree。2.3 一个容易被忽视的细节分支状态还有一个细节值得单独说Current checkout 会继承你当前所在的分支。如果你现在在某个功能分支上Codex 的改动就直接落在这个分支上。这本身没问题但如果你接下来打算切分支或者这个分支还有别的用途就要提前想清楚。我一般的做法是用 Current checkout 之前先确认三件事当前分支是不是我想让改动落地的分支、工作区有没有未提交的改动、这些改动会不会和即将进行的任务冲突。这三件事花不了十秒钟但能避免很多返工。提示如果你不确定当前工作区是否干净在让 Codex 动手之前先跑一次状态查看把未提交的文件列出来扫一眼。这个习惯能帮你挡掉大部分改动被覆盖的事故。3. New worktree 到底新在哪里3.1 它借的是 Git worktree 的能力New worktree 这个名字里的 worktree指的就是 Git 原生的worktree机制。简单说Git 允许同一个仓库同时挂载多个工作目录每个目录可以检出不同的分支但它们共享同一份版本历史。你在其中一个目录里的提交在另一个目录里也能看到因为历史是共享的但工作区的文件是各自独立的。Codex 的 New worktree 就是基于这个机制它会在你当前仓库之外另开一个工作目录通常是一个临时路径然后在这个新目录里执行任务。你原来的目录完全不受影响该是什么状态还是什么状态。这个设计的价值在于隔离。新目录里的改动、新目录里的分支、新目录里的未提交内容全都和你的主目录隔开。Codex 在里面怎么折腾都不会碰到你手头正在改的东西。3.2 隔离带来的三个实际好处第一个好处是可以并行。你可以在主目录里继续做自己的事同时让 Codex 在 worktree 里跑另一个任务两边互不干扰。这对那种我想同时验证两个方案的场景特别有用。以前要这么做得手动 clone 一份仓库或者 stash 来 stash 去现在一个选项就解决了。第二个好处是失败成本低。如果 Codex 在 worktree 里的改动不理想你直接把这个目录删掉就行主目录干干净净一点痕迹都不留。用 Current checkout 的话改动是直接落在你主目录里的清理起来要麻烦得多尤其是当它改了一堆文件的时候。第三个好处是分支干净。New worktree 通常会基于一个干净的分支状态开始不会把你主目录里那些乱七八糟的未提交改动带进去。这意味着 Codex 看到的代码是纯净的它做出的判断和改动也更可预测。3.3 代价是什么天下没有免费的午餐New worktree 的代价主要体现在两个方面。一是环境成本。新目录是一个全新的工作目录如果你的项目需要安装依赖、构建产物、配置本地环境变量这些在新目录里可能都要重来一遍。对于依赖很重的项目比如前端项目动辄几百兆的 node_modules这个成本不能忽略。我遇到过好几次worktree 建好了结果因为依赖没装Codex 跑起来各种报错最后还得手动去补环境。二是管理成本。worktree 用完是要清理的。如果你忘了删磁盘里会慢慢堆积一堆临时目录。Git 本身提供了查看和清理 worktree 的命令但前提是你得记得去用。我现在的习惯是任务一结束就顺手清理绝不拖到以后再说。4. 按任务类型做选择一张对照表光讲原理还是容易犯迷糊我把自己常用的判断逻辑整理成了一张表按任务类型来对照基本能覆盖八成以上的场景。任务类型推荐选项核心理由修一个明确的 bug改动范围小Current checkout就地改完就地提交流程最短加一个小功能不涉及大范围重构Current checkout同上且不需要额外环境当前工作区有未提交改动New worktree避免改动被覆盖或混淆想同时验证两个互斥方案New worktree隔离是刚需主目录保持不动探索性任务不确定结果如何New worktree失败直接删目录零成本回退依赖很重、环境搭建麻烦的项目Current checkout省去重装依赖的时间需要长时间运行、中途可能中断New worktree不阻塞主目录的日常使用改动需要立刻 review 并提交Current checkout改动就在眼前无需切换这张表不是死规矩但它背后的判断维度是清晰的看隔离需求和环境成本哪个更重要。隔离需求强有未提交改动、要并行、要试错就选 New worktree环境成本高依赖重、配置麻烦就倾向 Current checkout。两者都强的时候就得权衡一下我一般会优先保证隔离因为环境问题是可以解决的改动被覆盖的损失往往更大。4.1 一个具体的决策例子举个我最近遇到的场景。当时我在主目录里改一个数据处理模块改到一半突然发现另一个模块有个明显的逻辑错误需要修。这两个改动互不相关但都在同一个仓库里。如果我直接用 Current checkout 去修那个逻辑错误Codex 很可能会碰到我正在改的文件因为两个模块有共享的工具函数风险不小。所以我选了 New worktree让 Codex 在新目录里修那个逻辑错误。修完之后我在新目录里 review、提交然后把那个提交 cherry-pick 回主分支。整个过程主目录的改动一点没受影响两边都干净。这个例子里隔离的价值体现得很明显。如果当时图省事用 Current checkout很可能就是一场混乱。4.2 反过来什么时候我坚决不用 New worktree有一类项目我基本不会用 New worktree依赖特别重、环境配置特别繁琐的。比如某些需要编译原生模块的项目或者需要连接本地数据库、消息队列才能跑起来的项目。这类项目在新目录里重新搭一遍环境时间成本太高有时候还会因为路径变化导致配置失效。这种项目我宁愿先把主目录的改动提交或者暂存起来把工作区弄干净然后用 Current checkout。虽然多了一步清理工作区的操作但比重新搭环境划算得多。5. 实操中的完整流程与命令细节5.1 用 Current checkout 之前该做什么用 Current checkout 之前我固定会做两件事。第一件是查看工作区状态。这一步的目的是确认没有意外的未提交改动。有时候你自己都忘了昨天改了什么扫一眼能避免很多问题。如果发现有未提交的改动先判断它们会不会和即将进行的任务冲突。会冲突的话要么先提交要么先暂存。第二件是确认当前分支。如果你不希望改动落在当前分支上就得先切到目标分支。这一步很容易被跳过但一旦落错分支后面要挪动提交就麻烦了。# 查看当前工作区状态 git status # 查看当前所在分支 git branch --show-current # 如果有未提交改动且暂时不想提交可以先暂存 git stash push -m 临时保存日志模块调整暂存这个操作我用了很多次它相当于给你的未提交改动拍个快照然后把工作区恢复干净。等 Codex 的任务做完、提交之后再把暂存的内容恢复回来。这样既保证了工作区干净又不会丢失手头的改动。5.2 用 New worktree 时的环境处理New worktree 建好之后第一件事是确认环境。我一般会按这个顺序检查依赖有没有装、配置文件在不在、构建产物需不需要重新生成。对于依赖如果项目用的是常见的包管理器通常在新目录里跑一次安装命令就行。但要注意有些项目的依赖安装脚本会写死路径或者依赖主目录里的某些文件这种情况下新目录里可能会失败。遇到这种问题我的处理方式是手动把必要的配置复制过去或者临时改一下脚本里的路径。# 在新 worktree 目录里安装依赖以常见包管理器为例 cd /path/to/new-worktree npm install # 如果项目有构建步骤先跑一次构建 npm run build环境确认没问题之后再让 Codex 开始干活。这个顺序很重要如果环境没弄好就让它跑它可能会因为各种报错而做出奇怪的改动反而增加清理成本。5.3 任务结束后的清理New worktree 用完一定要清理这是我踩过坑之后养成的习惯。清理分两步先确认里面的改动都已经处理完该提交的提交了该丢弃的丢弃了然后删除这个 worktree。# 查看当前仓库有哪些 worktree git worktree list # 删除指定的 worktree git worktree remove /path/to/new-worktree # 如果目录里有未提交改动导致删不掉可以强制删除 git worktree remove --force /path/to/new-worktree强制删除这个选项要慎用它会连同未提交的改动一起丢掉。用之前一定确认里面没有你还需要的改动。注意worktree 的清理不只是删目录还要让 Git 知道这个 worktree 已经不存在了。用git worktree remove而不是直接rm -rf后者会留下 Git 的元数据残留时间长了git worktree list里会出现一堆幽灵条目。6. 那些文档里不会写的坑6.1 未提交改动被覆盖的真实案例前面提过一次改动被覆盖的经历这里展开说下细节因为它太典型了。当时的情况是我在主目录里改一个配置文件改到一半让 Codex 用 Current checkout 去加一个日志功能。Codex 在实现日志功能时需要读取配置文件来获取日志级别于是它顺手把配置文件也改了——加了一个默认的日志级别字段。问题是它改的那一行正好是我正在编辑的那一行。结果就是我的修改和它的修改混在一起而且因为它的改动是后写入的我的部分内容被覆盖了。事后复盘根本原因是我没有保证工作区干净。如果当时用 New worktree或者先把配置文件的改动提交/暂存这个事故就不会发生。所以我现在有一条铁律只要工作区有未提交改动就默认用 New worktree除非我百分之百确定改动不会重叠。6.2 worktree 里的分支陷阱New worktree 会检出某个分支这里有个容易踩的坑如果你指定的分支已经在主目录里被检出了Git 默认不允许同一个分支在两个 worktree 里同时检出。这时候 Codex 可能会自动创建一个新分支或者报错。自动创建新分支这个行为本身没问题但如果你没注意到后面提交的时候可能会发现改动落在了一个你没预期的分支上。我的做法是用 New worktree 时主动指定一个明确的新分支名而不是让它自己决定。# 创建 worktree 时指定新分支 git worktree add -b feature/temp-task /path/to/new-worktree这样分支名是可控的后面不管是合并还是删除都清楚自己在操作什么。6.3 磁盘空间的隐形消耗worktree 是完整的工作目录意味着它会占用和主目录差不多的磁盘空间取决于项目大小。如果你的项目有几个 G每开一个 worktree 就多几个 G。我有一段时间没注意清理磁盘空间悄悄少了一大截查了半天才发现是 worktree 堆积。现在的习惯是每次用完 worktree当天就清理。如果任务需要跨天我会在任务清单里记一笔提醒自己第二天处理完就删。6.4 编辑器工作区的重新配置如果你用 IDE 打开项目New worktree 是一个新路径IDE 需要重新打开这个目录相关的插件配置、调试配置、运行配置可能都要重新设一遍。对于配置复杂的项目这个成本不低。我的应对方式是把常用的运行和调试配置做成项目内的共享配置比如放在项目目录里的配置文件这样新 worktree 打开时能直接复用不用手动重配。这个习惯帮我省了不少时间。7. 我个人的选择习惯与几条经验用到现在我的选择逻辑已经比较固定了总结下来就是几条简单的规则。规则一工作区不干净一律 New worktree。这条没有例外。改动被覆盖的代价太高不值得为了省一点环境搭建时间而冒险。规则二探索性任务一律 New worktree。探索意味着结果不确定可能改了一堆东西最后发现方向不对。这种任务用 New worktree失败直接删目录主目录一点不受影响。规则三依赖重、环境搭建麻烦的项目优先 Current checkout。前提是工作区干净。这种情况下重新搭环境的成本太高不值得。规则四任务做完立刻清理。不管是提交还是删除不要拖。拖着的后果就是磁盘堆积和状态混乱。还有一条不算规则但很重要的经验不要在两个选项之间反复横跳。我见过有人一个任务里先用 Current checkout 改了一半觉得不对又切到 New worktree 重来结果两边都有改动最后自己都搞不清哪个是最新的。选定一个就做到底中途要换的话先把当前状态处理干净。最后说一个我最近才用顺手的技巧如果任务比较复杂我会先用 New worktree 做一版验证思路可行之后再把改动整理成干净的提交应用到主目录。这样主目录里留下的都是经过验证的改动不会有中间过程的噪音。这个流程比直接在 Current checkout 里试错要清爽得多尤其适合那种我知道大概怎么做但细节需要调的任务。这套习惯不是一天形成的中间踩过的坑、丢过的改动、清理过的临时目录都是学费。希望这些经验能帮你少走点弯路把精力花在真正重要的代码上而不是和工具的工作区状态较劲。