Agent 需要什麼樣的基礎工具集


看到大家在聊 Agent 工具集的問題——是不是提供一個 shell 就都搞定了?做了 holon 之後發現,其實沒有那麼簡單。
讀:為什麼放棄了 Read/Glob,全走 shell
holon 的工具集改了幾個版本,最後廢棄了類似 Claude Code 提供的 Read(讀檔案)、Glob(模式搜尋)這類專用工具,讀取和查找全部通過 shell 來完成。這和 Codex 的路線一致——Codex 的 ExecCommand 一把梭,讀檔就是 cat,搜程式碼就是 rg,不再單獨為每種"讀"操作定義一個工具。
這樣做的理由很樸素:shell 是 LLM 最熟悉的"程式語言"。與其讓模型去學你定義的 Read 工具的參數語義,不如直接讓它寫已經訓練了數十億次的 shell 命令。每多一個專用工具,模型的認知負擔就加一層;而 shell 這個界面,模型已經足夠熟練了。
但全走 shell 有一個代價:輸出截斷。框架為了避免 shell 返回值太長撐爆上下文,會給每個命令設輸出上限。Agent 用 cat 讀一個大檔案,可能只拿到前半截,剩下的在 artifact 檔案裡,還得再 cat 一次甚至多次才能讀完。Claude Code 的 Read 工具壓縮閾值比通用 shell 高很多,讀大檔一步到位,少了好幾個來回。本質上是取捨:少定義工具降低認知負擔,但專用工具在邊界場景效率更高。
寫:從 sed 到 ApplyPatch,以及 free grammar tool 的難題
但寫操作就無法完全用 shell 搞定。
如果讓 Agent 全用 sed 做編輯,就會發現遇到複雜的多行匹配很難處理——換行、轉義、縮排,任何一層出了問題都會導致編輯失敗。所以很多系統會提供 Replace String 這樣的編輯工具,讓 Agent 傳一大段 old_string 來精確匹配並替換成 new_string。雖然笨拙,但比 sed 穩得多。
Codex 則走得更遠,發明了自己的 ApplyPatch 工具,讓 Agent 直接生成 patch,一次搞定批量編輯。holon 就借鑑了這個思路。
但落地時踩到一個坑:Codex 用的是一套 OpenAI 自己定義的簡化 patch 格式,並且搭配了一種叫做 free grammar tool 的特殊工具機制來解決格式傳遞問題。
為什麼要專門搞一種新機制?因為 LLM 的標準工具定義都是 tool(args) 這種 JSON 參數格式。如果把 patch 作為 JSON 字串參數傳遞,會牽扯到大量的轉義——換行要變成 \n,引號要加反斜杠,縮排也得小心處理。Agent 寫 patch 時本身就容易出錯,再疊一層 JSON 轉義,出錯概率翻倍。free grammar tool 的思路是把 patch 的原始文本直接作為 tool 的輸入體,不經過 JSON 參數編碼,模型寫什麼就是真正的內容。這大幅降低了模型生成 patch 時的出錯率。
而這套機制目前只有 OpenAI 的 Codex 接口支持。holon 是要兼容多模型提供方的,沒法只靠這一條路。
於是 holon 的做法是:根據模型注入不同的 ApplyPatch 定義。對支持 free grammar 的模型,直接走原始 patch 格式;對其他模型,就接收標準的 git diff 格式。我覺得 LLM 經過 GitHub 上數十億次 diff 的訓練,對 git diff 格式應該相當熟練。實踐下來效果還可以——雖然也常出錯,但多數時候能改對,而且隨著訓練數據積累,這個能力只會越來越好。不過我還是建議各家模型廠商都支持一下 free grammar tool,這對 Agent 寫程式的場景確實是剛需。
調度:長時間命令和 task 抽象
第三個問題是 Agent 執行的 shell 命令不一定會很快結束——啟動 dev server、跑測試、構建專案,都可能跑很久,甚至根本不退出。早期的 Agent 框架處理得很粗暴:要麼同步阻塞把自己卡死,要麼所有命令一律丟背景,結果 Agent 把同一個命令反覆執行很多遍。
現在業界逐漸收斂到一個基本共識:不給 Agent 暴露"前台/背景"的選擇——這件事 Agent 自己判斷不準。更好的方式是設置一個時間閾值,命令超時自動轉背景,對 Agent 完全透明。Agent 不需要預判這個命令該不該放背景,runtime 自己處理就行。
但自動轉背景只是第一步。轉背景之後,真正的工程問題才浮出來——而這些問題,目前業界還沒有標準答案。
首先是輸出怎麼讀。背景任務可能還在跑也可能已經結束,輸出可能很大。但各家 API 的語義並不統一——有的走輪詢,有的走事件推送。
其次是任務怎麼停。各家都有取消機制,但取消是即時 kill 還是優雅退出、已產生的部分輸出要不要保留?
最後是誰來叫醒 Agent。Agent 把任務丟背景以後休眠了,任務結束那一刻誰來叫醒它?這要求 runtime 和 Agent 調度深度綁定,不是獨立工具層能解決的。
這三件事——讀輸出、停任務、叫醒 Agent——合在一起,就是背景任務完整的生命週期管理。各家都實現了"能背景跑",但管理層還沒有標準化方案,這可能是下一階段 Agent 工具鏈演進的關鍵節點。
還沒到無腦用一個現成模式的時候
所以回到開頭的問題:shell 能解決 80%,但剩下 20%——編輯的精確性、patch 格式與模型能力的匹配、長任務的調度抽象——恰恰決定了 Agent 能不能從 demo 走向真正可用的系統。
工具集的選擇遠不止"封裝一個 shell"那麼簡單,也遠沒到大家可以無腦套用一個現成模式的時候。這也是為什麼 Codex 和 Claude Code 在這些基礎問題上給出了不同的答案,而 holon 又根據自己的場景做了不同的取捨,這中間可以探索和改進的點還很多。
查看原文
此頁面可能包含第三方內容,僅供參考(非陳述或保證),不應被視為 Gate 認可其觀點表述,也不得被視為財務或專業建議。詳見聲明
  • 打賞
  • 回覆
  • 轉發
  • 分享
回覆
請輸入回覆內容
請輸入回覆內容
暫無回覆
  • 已置頂