<cite id="ffb66"></cite><cite id="ffb66"><track id="ffb66"></track></cite>
      <legend id="ffb66"><li id="ffb66"></li></legend>
      色婷婷久,激情色播,久久久无码专区,亚洲中文字幕av,国产成人A片,av无码免费,精品久久国产,99视频精品3
      網易首頁 > 網易號 > 正文 申請入駐

      用好你的jj - 重新思考Agent時代的版本控制

      0
      分享至

      本文轉載自:《用好你的 jj - 重新思考 Agent 時代的版本控制》

      作者:王巍 (onevcat)

      原文鏈接:https://onevcat.com/2026/03/jj-for-agent-era/

      作品采用 CC BY 4.0 知識共享許可協議。


      過去大半年我一直在高強度地用 AI agent 寫代碼,用著用著發現一個問題:“怎么組織 agent 吐出來的東西”這件事,比我原來想的重要太多了。

      這話聽著可能有點奇怪。大家關心的一般都是模型能力、prompt 怎么寫、上下文夠不夠長…… 但真的和 agent 密集配合過一陣子之后,你會發現有個更底層的東西一直在拖后腿:版本控制。說得再具體一點,就是你拿什么樣的心智模型來管理本地的代碼變更。

      我現在的結論是:Git 作為遠端協作和代碼托管的標準還是沒什么好說的,但在本地工作流這頭,jj (https://github.com/jj-vcs/jj) 明顯更適合現在這種人和 agent 來回切著干活的開發方式。這篇文章就是來安利這個的。

      Git 在 Agent 時代的摩擦

      Git 是個偉大的工具,這一點沒啥好爭的。但它的很多設計假設,是建立在二十年前“人類手工編程”的時代背景上 —— 一個人坐在編輯器前面,想清楚要改什么,改完檢查一遍,然后addcommitpush。這套流程是給人類的線性思維量身做的:staging area 給你一個“最后再看一眼”的機會,branch 幫你隔離不同的工作流,stash 讓你臨時把手頭的東西放一放。

      說白了,這些機制就是給人類留一口喘氣的時間。

      但 agent 不需要喘氣。

      agent 一介入開發,staging area、detached HEAD、rebase in progress、stash 棧 —— 這些隱性狀態全都變成了絆腳石。Agent 不理解這些狀態,也沒必要理解。但你為了讓 agent 正確操作 Git,又不得不把這些狀態信息當成額外上下文喂給它,白白浪費 token。

      這里有個要緊的觀察:agent 的干活方式是“先嘩嘩地生成一堆,回頭再整理歷史”,而 Git 的模型偏向“邊想邊提交”。這兩件事天然就是擰著的。

      想想你有多少次在心流里把自己打斷,跟 agent 說“提交一下”“先 stash 一下”“切到那個分支”。每一次都是一次脫軌 —— 你從“想產品想代碼”切到了“想 Git 狀態管理”。以前沒有 agent 的時候,這點開銷還能忍;但你和 agent 配合的節奏越快、頻率越密,每次打斷的代價就越高。

      jj 和 Change:一個更簡單的心智模型 jj 的定位

      jj 是一個可以和 Git 無縫共存的版本控制工具。本地用 jj 管理變更,遠端依然通過jj git push/fetch和標準 Git 交互 —— 對 GitHub 和你的同事來說,看到的就是普通的 git commit 和 branch,沒有任何區別。

      也就是說你可以隨時試試看,不喜歡也可以隨時退回 Git,沒有遷移成本,不存在被鎖定的問題。

      安裝也就一行的事:

      brewinstall jj
      cdyour-repo
      jjgit init --colocate
      用一個例子理解 Change

      jj 的核心概念是change。與其列一堆定義,不如直接上手看看。

      假設你在一個現有 repo 里剛啟用了 jj,跑一下jj log

      @  kxryzmsp  (empty) (no description set)
      ○ master

      @表示你當前所在的 change,kxryzmsp是它的Change ID—— 一個跨 rebase 不變的唯一標識。你不需要記 branch name 或 commit hash,這個短 ID 就是你在 jj 世界里的坐標。一般來說,你甚至可以只用前兩個或者前三個字母來代表它。

      現在開始寫代碼。改了幾個文件后,再跑jj log

      @  kxryzmsp  (no description set)
      │ modified: src/auth.rs, src/main.rs
      ○ master

      注意:你什么都沒做,改動已經屬于當前 change 了。沒有git add,沒有 staging area,不存在“改了但還沒 add”這種中間態。在 jj 里,你的 working copy 本身就是一個 change,文件一改,它就跟著變。

      這段工作做完了,給它一個描述:

      jj describe -m "feat: add auth module"

      這就像寫 commit message,但有一個重要區別:隨時可以改。甚至可以對任意 change 改(jj describe -r -m "..." ),不需要rebase -i來修改歷史消息。

      開始下一項工作:

      jjnew

      @  wqnyzlkr  (empty) (no description set)
      ○ kxryzmsp feat: add auth module
      ○ master

      jj new做的事情很簡單:把當前 change 定格,創建一個新的空 change 作為你的新工作臺。相當于 Git 的commit+ 開始新工作,但不需要add這個步驟。(順便一提,為了照顧git習慣,jj commit也存在:jj commit -m "..."就是describe+new的 alias。)

      幾個 change 下來,你的jj log可能長這樣:

      @  tpqrstuv  (empty) (no description set)
      ○ wqnyzlkr feat: add token refresh
      ○ kxryzmsp feat: add auth module
      ○ master

      到這里,你其實已經理解了 jj 80% 的日常。接下來幾個操作也很直觀。

      分叉:jj new

      從某個 change 開始新工作,不影響原來的鏈:

      jjnew kx

      ○  wqnyzlkr  feat: add token refresh

      │ @ mnopqrst (empty) (no description set)
      ├─╯
      ○ kxryzmsp feat: add auth module
      ○ master
      回到舊 change 繼續修改:jj edit

      jjedit kx

      直接跳回那個kxryzmspchange 繼續改代碼。改完后,后續所有 change 自動 rebase,沒有 detached HEAD,也不需要手動操作。

      值得一提的是:對于已經推送到遠端的 immutable change,jj edit會直接報錯(Error: Commit is immutable ),防止你意外改寫已發布的歷史。jj 在工具層面幫你守住了這個安全邊界,你不需要自己記住” 這個能不能改”。

      Merge:給jj new傳多個 parent

      jjnew wqnyzlkr mnopqrst
      # 當然,只要不重復,你也可以寫
      # jj new wq mn

      @  uvwxyzab  (empty) (no description set)
      ├─╮
      ○ │ wqnyzlkr feat: add token refresh
      │ ○ mnopqrst fix: hotfix for auth
      ├─╯
      ○ kxryzmsp feat: add auth module
      ○ master
      Rebase

      mnopqrst移到wqnyzlkr后面:

      jjrebase -s mnopqrst -d wqnyzlkr

      @mnopqrst  fix:hotfixforauth
      ○wqnyzlkr feat:addtokenrefresh
      ○kxryzmsp feat:addauthmodule
      ○master

      原本分叉的兩條線變成了一條直線,就這么簡單。

      和遠端 Git 交互

      jj 通過bookmark和 Git 世界橋接。jj git fetch時,遠端的 Git branch(比如master)會自動映射為 jj 的 bookmark—— 所以你在jj log里看到的master就是遠端的masterbranch。

      拉取并 rebase 到最新:

      jjgit fetch
      jjrebase -d master

      相當于 Git 的git pull --rebase,但拆成了兩個明確的步驟:先拿數據,再決定怎么整合。

      推送時反過來,給你的 change 貼一個 bookmark(映射成 Git branch):

      jjbookmark create my-feature -r wqnyzlkr
      jjgit push

      Bookmark 只在和遠端交互時才需要,本地工作幾乎不用想 branch 這個概念。

      這些就是 jj 的全部日常了。沒有 staging area,沒有 detached HEAD,沒有 stash 棧。光是這些,日常在本地干活就已經清爽不少了。但 jj 真正讓我覺得“這東西必須推薦給別人”的地方,是它和 agent 工作流之間的那種天然的契合感。

      實戰場景:當 jj 遇上 Agent 工作流

      接下來是我最想聊的部分。每個場景我都會列出 Git 時代的做法 —— 包括你可能會對 agent 說的話 —— 和 jj 下的做法。一對比就很清楚了。

      場景 1:最簡單的日常 —— 開始下一項工作

      Git 時代

      你:看看現在的改動情況,把這些變更提交并推送,
      然后新建一個分支,開始下一項工作:實現用戶頭像上傳功能

      工作結束后:

      你:檢查一下改動,沒問題的話提交并推送

      每項工作的開頭和結尾,你都得指揮 agent 走一遍“檢查 → add → commit → push”的儀式,開始新工作前還得記著建分支。這些指令跟你真正想做的事情一點關系都沒有,但一天可能得說上好幾遍。

      jj

      你:開始下一項工作:實現用戶頭像上傳功能

      jj 永遠是“干凈”的,Agent 直接無腦jj new就可以開始干活。甚至可以jj describe -m "feat: avatar upload"后在這個 change 上直接工作。不需要 add,不需要顯式 commit。當你需要推送時,再貼 bookmark 并 push。

      版本控制從“每次都要交代的儀式”變成了“背景里自然發生的事”。

      場景 2:做到一半,臨時切去處理別的事

      Git 時代

      你:先 stash 一下,切到 master,拉最新代碼,新建一個分支來修這個 bug

      Agent 需要執行git stash → git checkout master → git pull → git checkout -b hotfix → ...修完... → git checkout - → git stash pop。這個鏈條中間任何一步出了岔子(比如 stash 沖突),agent 都可能卡住或者搞出更多問題來。

      jj

      你:先去修一下那個 bug

      Agent 只需要jj new master,在新 change 里修 bug,修完后jj edit回到之前的 change 繼續。沒有 stash,沒有分支切換,沒有什么狀態要恢復。

      場景 3:完成工作后,拆分變更內容

      這大概是日常里最常見的整理場景了:agent 完成了一項(甚至多項)工作,產出了一大坨改動,現在你需要把它們拆成邏輯清晰的提交歷史。

      Git 時代

      你:檢查我們的變更,按照修改的邏輯進行合理拆分,
      并多次提交,保持 commit 合理可追溯

      說實話,這對 agent 來說挺難的。它需要理解整個 diff、想好怎么拆,然后git reset HEAD~1,再git add -p交互式地選 hunk—— 或者手動git add特定文件然后 commit,來回好幾次。這個過程非常脆弱:agent 很容易 add 的時候漏掉文件,少選幾行,或者把不相關的改動混進同一個 commit。

      jj

      你:按模塊拆分當前 change:功能實現、測試、文檔各一個

      Agent 執行jj split,選擇文件或 hunk 歸到第一個 change,剩下的自動成為第二個。再jj split一次就拆成三個。全程沒有“暫存區”這個概念,也永遠不會丟東西,不存在“reset 后忘了 add 某個文件”的風險。拆分錯了就回去 edit,后面的 changes 自動 rebase。

      場景 4:先規劃骨架,再讓 agent 分段實現

      我個人覺得這是 jj 在 agent 工作流里最厲害的用法。

      Git 時代

      基本沒有什么對應的自然操作。你頂多在一個外部文檔里列出步驟,然后讓 agent 一個個做完再 commit。但如果中間某步需要回頭改前面的實現,整個提交歷史就得用rebase -i來整理 —— 光是跟 agent 解釋清楚怎么 interactive rebase,就夠燒一輪上下文了。

      jj

      先創建一串 change 骨架,每個都是空的,只有描述(jj的提交格式和git一致:首行作為標題,后續空行后作為描述,所以你也完全可以在-m后面寫小作文甚至 prompt):

      jj commit -m "refactor: extract auth module"
      jj commit -m "feat: add token refresh logic"
      jj commit -m "test: update auth tests"
      jj commit -m "docs: update API documentation"

      然后對 agent 說:

      你:參考各 change 的描述,從 kxry 開始,順次處理每個 change 的實現

      Agentjj edit到第一個 change,寫代碼;寫完后jj edit到下一個。每個 change 填充完后,后續 change 自動 rebase,不需要任何手動操作。

      還有個比較野的玩法:agent 甚至可以拿描述本身當驗收標準 —— 你把測試方法和通過條件都寫在-m里,或者把你的 spec 拆成一堆骨架 change。Agent 跑完一個步驟,自己對照描述確認達標了,才往下走 —— 這就自然形成了一個自驅動的循環。在 Git 里搞這種事情,你得額外維護一份文檔,agent 來回對照,可能還得配合 Ralph Loop 之類的東西才行,遠沒有直接把標準寫進 change 描述來得順手。

      場景 5:多 agent 并行開發

      多 agent 并行在現在的開發里越來越常見了,Git 那邊git worktree已經是很多團隊的標配。jj 通過 workspace 提供了對等的能力:

      jjworkspace add ../agent-1
      jjworkspace add ../agent-2
      jjworkspace add ../agent-3

      每個 workspace 有獨立的磁盤目錄,但共享底層 store。多個 agent 同時從同一個 base 分叉干活:

             → b1 (agent 1)
      base → b2 (agent 2)
      → b3 (agent 3)

      做完后jj new b1 b2 b3合并。和git worktree比的話,jj workspace 不需要提前建 branch,也不需要一個個合并搞出一堆 merge commit,配合 change 模型用起來更順手一些,不過核心能力是對等的。選 jj 不會在多 worktree 并行的場景下丟掉什么能力。

      場景 6:Agent 搞砸了,需要快速回退

      這件事幾乎一定會發生,而且會經常發生。

      Git 時代

      你:撤回剛才的修改。
      你:什么?操作丟了?你上下文里還有么?(大汗...)

      Agent 得先判斷現在是啥情況:該用git reset --hardgit checkout .git revert?還是得翻git reflog找到之前的狀態再reset?每種選擇的副作用都不一樣,選錯了可能把工作成果弄丟,一天白干。

      jj

      你:撤回剛才的操作

      Agent 執行jj undo。一個命令,撤回最后一個操作,不管那個操作具體是什么。如果需要回退到更早的狀態,jj op log查看操作級別的歷史,jj op restore 恢復到任意節點。什么都不會真正丟。

      小結

      回頭看這些場景,jj 的好處不光是“少打幾個命令”或者“步驟簡單一些”。更要緊的是:你跟 agent 說話的時候可以只說業務上的事,不用操心版本控制的狀態。

      當你不再需要說“先 stash”“切到那個分支”“interactive rebase 一下”的時候,你和 agent 之間的溝通帶寬才算真正被釋放出來了。你腦子里想的是產品邏輯和代碼設計,而不是 Git 的狀態機怎么轉。

      在 AI 時代,更重要的能力不是“一次生成完美的提交歷史”,而是“低成本地把已有結果整理成合理的歷史”。jj 的設計,恰好就是在做這件事。
      最小可用命令速查

      如果你看到這里已經有點心動了,下面這張表就是你需要的全部。十個命令,覆蓋 jj 的日常使用:

      操作

      jj

      Git 等效

      查看狀態和歷史

      jj loggit log --oneline --graph

      +git status

      給當前改動寫描述

      jj describe -m "..."git commit -m "..."

      (但 jj 可隨時改)

      開始下一段工作

      jj newgit commit

      + 繼續編輯

      切到某個 change 繼續編輯

      jj edit git checkout

      (但不會 detach)

      拆分一個 change

      jj splitgit reset HEAD~1

      + 反復git add -p+git commit

      撤回上一步操作

      jj undogit reflog

      +git reset

      拉取遠端

      jj git fetchgit fetch

      Rebase 到最新 master

      jj rebase -d mastergit rebase master

      標記要推送的 change

      jj bookmark create feat -r @git branch feat

      推送

      jj git pushgit push

      會這些就夠了。剩下的,邊用邊學。

      讓 Agent 直接用上 jj

      一般來說直接讓你的 agent 使用 jj 就好,它的生態和 agent 對它的認識,基本可以做到無縫切換,你只需要在 AGENTS.md 或者 CLAUDE.md 提上一句“這個 repo 在本地使用jj管理”,然后按照jj的方式組織提示詞并工作就好。

      但如果你想要給你的 agent 喂一個更精確的操作指南的話,我也配套制作了一個 jj 的 agent skill:onevcat-jj(https://github.com/onevcat/skills/tree/master/skills/onevcat-jj),讓它可以更好地理解和使用 jj 來管理版本控制 —— 包括本文提到的所有場景。

      如果你的 agent 工具支持 skills.sh 生態,一行命令就能安裝:

      npxskills add onevcat/skills --skill onevcat-jj

      如果你裝了 OMA (Oh My Agents),點一下就能裝:

      或者,你也可以直接把下面這段話丟給你的 agent,讓它自己搞定:

      讀取 https://github.com/onevcat/skills/tree/master/skills/onevcat-jj 的
      SKILL.md 內容,將它作為一個 skill 安裝到本地。詢問我希望安裝到用戶全局
      還是當前項目,然后把文件放到對應的 skills 目錄。

      Git 在過去二十年里定義了現代軟件開發的協作方式,不管是慣性使然還是生態積累,我想這個地位在很長一段時間內都不會變。但“協作”和“本地工作”是兩碼事。Git 在協作這頭還是沒得說的標準;而在本地這頭 —— 你怎么組織變更、怎么整理歷史、怎么和 agent 配合 —— 也許確實到了該重新想想的時候了。

      jj 給出的答案挺樸素的:把那些為人類心理安全感設計的中間狀態砍掉,讓版本控制的心智模型回到最簡單的樣子。當 agent 越來越深地參與到日常開發里,這種低成本地重寫、拆分、回退和并行的能力,只會越來越重要。

      Git 仍然是你和世界協作的語言;但 jj 可能是你和 agent 一起思考的更好方式。

      特別聲明:以上內容(如有圖片或視頻亦包括在內)為自媒體平臺“網易號”用戶上傳并發布,本平臺僅提供信息存儲服務。

      Notice: The content above (including the pictures and videos if any) is uploaded and posted by a user of NetEase Hao, which is a social media platform and only provides information storage services.

      相關推薦
      熱點推薦
      謝霆鋒武漢演唱會快哭了,臉頰斑點明顯眼袋重,一身中年男油膩感

      謝霆鋒武漢演唱會快哭了,臉頰斑點明顯眼袋重,一身中年男油膩感

      小娛樂悠悠
      2026-04-12 10:28:21
      蘋果首款折疊屏來了!iPhone Ultra將徹底解決折疊屏兩大缺陷

      蘋果首款折疊屏來了!iPhone Ultra將徹底解決折疊屏兩大缺陷

      快科技
      2026-04-13 07:31:04
      湖北農民被蛇群“追殺”5年,死后墳墓變成蛇墳,他當年做了啥?

      湖北農民被蛇群“追殺”5年,死后墳墓變成蛇墳,他當年做了啥?

      神奇故事
      2026-04-12 23:54:08
      勸退!“去客廳化”火了5年,為什么70%家庭最后都偷偷把沙發搬了回來?

      勸退!“去客廳化”火了5年,為什么70%家庭最后都偷偷把沙發搬了回來?

      繪本家居
      2026-04-10 11:13:39
      英偉達徹底退出中國市場,黃仁勛嘆息:傷害中國,美國受傷更嚴重

      英偉達徹底退出中國市場,黃仁勛嘆息:傷害中國,美國受傷更嚴重

      小熊侃史
      2026-04-11 10:30:48
      閉門會談一小時,只要和平不談統一?鄭麗文八字回應,大陸表態了

      閉門會談一小時,只要和平不談統一?鄭麗文八字回應,大陸表態了

      李健政觀察
      2026-04-12 12:34:13
      美媒:烏克蘭在3月份攔截3.3萬架俄無人機;難怪無人機讓美破防呢

      美媒:烏克蘭在3月份攔截3.3萬架俄無人機;難怪無人機讓美破防呢

      嘯鷹評
      2026-04-11 22:59:40
      韓女星樸娜萊和男性朋友在車上發生了性關系,兩名經紀人被迫圍觀

      韓女星樸娜萊和男性朋友在車上發生了性關系,兩名經紀人被迫圍觀

      西樓知趣雜談
      2026-04-09 09:35:17
      鄭麗文大陸行程結束,留下8句“金句”摘錄,真是超經典超有水平

      鄭麗文大陸行程結束,留下8句“金句”摘錄,真是超經典超有水平

      點點細語
      2026-04-12 22:46:34
      八路軍最悲壯的主力團,團長營長全戰死,副團長成了二野頭號虎將

      八路軍最悲壯的主力團,團長營長全戰死,副團長成了二野頭號虎將

      史之銘
      2026-04-12 16:48:19
      如果沒罰分,中超5強表現怎樣?國安距副班長僅2分,申花仍排第2

      如果沒罰分,中超5強表現怎樣?國安距副班長僅2分,申花仍排第2

      體壇鑒春秋
      2026-04-12 22:52:41
      36歲時的鄭麗文與蘭宣、尹乃菁合影。

      36歲時的鄭麗文與蘭宣、尹乃菁合影。

      草莓解說體育
      2026-04-12 08:02:43
      范戴克掀桌:票價漲9%沒商量,利物浦球迷集體破防

      范戴克掀桌:票價漲9%沒商量,利物浦球迷集體破防

      體壇觀察猿
      2026-04-13 06:42:40
      隨著廣東贏球、北京落敗,CBA又亂了!廣東重回第三,北京第四

      隨著廣東贏球、北京落敗,CBA又亂了!廣東重回第三,北京第四

      多特體育說
      2026-04-12 22:09:16
      真主黨:困獸猶斗,但時代潮水正在退去

      真主黨:困獸猶斗,但時代潮水正在退去

      原某報記者
      2026-04-10 23:36:21
      丈夫走后,妻子去兒子家過年,兒子一家人去吃飯,兒媳:你回家吧

      丈夫走后,妻子去兒子家過年,兒子一家人去吃飯,兒媳:你回家吧

      林林故事揭秘
      2025-05-17 17:44:06
      “我女兒敢這樣,腿給砸斷”,寶媽曬2個女兒出門,裝束讓人怒了

      “我女兒敢這樣,腿給砸斷”,寶媽曬2個女兒出門,裝束讓人怒了

      蝴蝶花雨話教育
      2026-04-10 13:01:09
      瞞不住了!鄭麗文訪陸,臺灣縣市長集體發聲

      瞞不住了!鄭麗文訪陸,臺灣縣市長集體發聲

      果媽聊娛樂
      2026-04-12 10:57:11
      煮米飯別只加清水!酒店不外傳秘訣,粒粒蓬松超好吃

      煮米飯別只加清水!酒店不外傳秘訣,粒粒蓬松超好吃

      開心美食白科
      2026-04-09 09:43:04
      摸景甜胸側,摟李雪琴胳膊,沒分寸感的他來《你好星期六》干嘛?

      摸景甜胸側,摟李雪琴胳膊,沒分寸感的他來《你好星期六》干嘛?

      老黯談娛
      2026-04-12 13:43:48
      2026-04-13 08:08:49
      開源中國 incentive-icons
      開源中國
      每天為開發者推送最新技術資訊
      7679文章數 34533關注度
      往期回顧 全部

      科技要聞

      4000億智譜,想變得更貴

      頭條要聞

      大伯為35歲女兒周末連跑3處相親角:女兒平時工作太忙

      頭條要聞

      大伯為35歲女兒周末連跑3處相親角:女兒平時工作太忙

      體育要聞

      創造歷史!五大聯賽首位女性主教練誕生

      娛樂要聞

      賭王女兒何超蕸病逝,常年和乳癌斗爭

      財經要聞

      美伊談判破裂的三大癥結

      汽車要聞

      煥新極氪007/007GT上市 限時19.39萬起

      態度原創

      手機
      時尚
      親子
      教育
      家居

      手機要聞

      三星 Galaxy Z Flip8渲染圖曝光,精致小折疊

      被周冬雨、林更新戴上熱搜的珠寶,究竟有多驚艷?

      親子要聞

      “晚上疼得睡不著”!8歲女童雙眼、身上被灼傷!警惕這東西,不少人家里有

      教育要聞

      教育部新推教改大動作!這場重量級活動千萬別錯過

      家居要聞

      復古風格 自然簡約

      無障礙瀏覽 進入關懷版