計(jì)原理與工程實(shí)踐:從認(rèn)知架構(gòu)到工具調(diào)用的完整指南)
最近在系統(tǒng)梳理 AI Agent 相關(guān)的知識(shí)體系翻了不少論文、框架文檔和工程博客也把《深入理解 AI Agent設(shè)計(jì)原理與工程實(shí)踐》這類書籍從頭到尾啃了一遍。讀下來最大的感受是AI Agent 的門檻不在“調(diào)大模型 API”而在“把規(guī)劃、記憶、工具調(diào)用、反思這些模塊組織成一個(gè)穩(wěn)定可靠的系統(tǒng)”。往往 Demo 跑通很容易一旦到了多輪任務(wù)、工具返回異常、上下文超長(zhǎng)、結(jié)果需要校驗(yàn)這些真實(shí)場(chǎng)景各種工程問題才會(huì)暴露出來。這篇文章主要圍繞 AI Agent 的設(shè)計(jì)原理與工程實(shí)踐展開會(huì)先講清楚 Agent 的核心概念和認(rèn)知架構(gòu)再給出一套可運(yùn)行的實(shí)戰(zhàn)代碼最后整理我在項(xiàng)目落地中遇到過的高頻問題和排查思路。適合剛接觸 Agent 開發(fā)、想系統(tǒng)理解原理的讀者也適合已經(jīng)寫過簡(jiǎn)單 Agent、但希望提升穩(wěn)定性和工程化水平的開發(fā)者。1. 背景與核心概念1.1 什么是 AI AgentAI Agent也就是智能體可以理解為一個(gè)“能自己做決策并執(zhí)行任務(wù)的 AI 程序”。它和普通對(duì)話機(jī)器人最大的區(qū)別是ChatBot 只負(fù)責(zé)“說”Agent 還要負(fù)責(zé)“做”。舉個(gè)具體的例子。你問普通 ChatBot“幫我查一下北京明天的天氣如果下雨就提醒我?guī)??!?ChatBot 大概率會(huì)給你一段話“好的我建議您使用天氣 App 查詢……” 因?yàn)樗鼪]有獲取實(shí)時(shí)數(shù)據(jù)的能力也沒有執(zhí)行后續(xù)動(dòng)作的入口。但 Agent 不一樣。它可以調(diào)用天氣查詢工具獲取北京明天的實(shí)時(shí)天氣判斷“下雨”這個(gè)條件是否成立如果成立調(diào)用提醒工具把提醒內(nèi)容推送到你的手機(jī)。這就是 Agent 的核心價(jià)值把大模型的“理解能力”和外部工具的“執(zhí)行能力”組合起來完成一個(gè)相對(duì)完整的任務(wù)閉環(huán)。1.2 Agent 與 RAG、Workflow 的關(guān)系很多讀者容易把 Agent、RAG、Workflow 混在一起這里先做一個(gè)區(qū)分。RAG檢索增強(qiáng)生成解決的是“知識(shí)不足”的問題。它先把外部文檔切片、向量化然后在用戶提問時(shí)檢索相關(guān)片段拼進(jìn) Prompt 讓大模型回答。RAG 的本質(zhì)是“增強(qiáng)模型的背景知識(shí)”。Workflow 解決的是“流程固定”的問題。它把一系列步驟寫死比如“先調(diào)用 A 接口再判斷結(jié)果然后走 B 分支”每個(gè)環(huán)節(jié)都是預(yù)先編排好的模型不參與決策。Agent 解決的是“動(dòng)態(tài)決策”的問題。模型根據(jù)當(dāng)前任務(wù)和上下文自己決定下一步調(diào)用哪個(gè)工具、什么時(shí)候結(jié)束。它比 Workflow 更靈活但代價(jià)是結(jié)果不可完全預(yù)期工程上需要更多兜底設(shè)計(jì)。這三者并不是互斥的。一個(gè)成熟的 Agent 系統(tǒng)內(nèi)部往往包含 RAG 組件也會(huì)用 Workflow 做流程編排。可以理解為Agent 是大腦RAG 是知識(shí)庫(kù)Workflow 是手腳的固定動(dòng)作模板。1.3 為什么需要掌握 AI Agent 開發(fā)從技術(shù)發(fā)展角度看大模型的能力正在從“生成文本”擴(kuò)展到“使用工具”“操作軟件”“完成復(fù)雜任務(wù)”。而不論是做一個(gè)企業(yè)知識(shí)庫(kù)助手、一個(gè)自動(dòng)化運(yùn)維機(jī)器人還是一個(gè)能寫代碼的 coding agent底層都離不開 Agent 的這套架構(gòu)。掌握了 Agent 開發(fā)意味著你不僅能調(diào)用模型還能設(shè)計(jì)一套讓模型“安全、穩(wěn)定、可控”地完成任務(wù)的系統(tǒng)。這也是 AI 應(yīng)用從“能聊”走向“能用”的關(guān)鍵一步。2. 環(huán)境準(zhǔn)備與版本說明本文的實(shí)戰(zhàn)部分會(huì)使用 Python OpenAI 兼容接口實(shí)現(xiàn)一個(gè)帶工具調(diào)用能力的 Agent。代碼核心思路不綁定具體廠商如果你使用的是其他 LLM 服務(wù)只要它支持 function calling 或者兼容 OpenAI 協(xié)議都可以用同樣的方式改造。2.1 開發(fā)環(huán)境操作系統(tǒng)Windows / macOS / Linux 均可編程語(yǔ)言Python 3.10 及以上包管理工具pip 或 poetryIDEVS Code、PyCharm 都可以關(guān)鍵是能方便調(diào)試2.2 Python 依賴本文示例用到的主要依賴如下openai用于調(diào)用大模型接口python-dotenv用于管理 API Key 環(huán)境變量requests用于調(diào)用外部 HTTP 工具接口可以執(zhí)行下面的命令安裝pip install openai python-dotenv requests需要提醒的是openai 這個(gè) SDK 更新迭代較快不同版本之間 API 簽名略有差異。本文代碼以常見的 1.x 版本為例編寫如果你使用的是其他版本以官方文檔為準(zhǔn)但整體的“聲明工具 - 模型返回工具調(diào)用 - 執(zhí)行工具 - 回填結(jié)果”流程是一致的。2.3 準(zhǔn)備 API Key在項(xiàng)目根目錄創(chuàng)建一個(gè).env文件OPENAI_API_KEYsk-xxxxxxxxxxxxxxxx OPENAI_BASE_URLhttps://api.openai.com/v1如果你使用的是國(guó)內(nèi)模型服務(wù)或本地部署的模型網(wǎng)關(guān)把OPENAI_BASE_URL改成對(duì)應(yīng)的地址即可。代碼中通過dotenv加載配置import os from dotenv import load_dotenv load_dotenv() api_key os.getenv(OPENAI_API_KEY) base_url os.getenv(OPENAI_BASE_URL)3. 核心設(shè)計(jì)原理拆解書里最值得反復(fù)讀的部分不是某個(gè)具體的框架 API而是 Agent 背后的設(shè)計(jì)原理。只有理解原理?yè)Q框架、換模型、換業(yè)務(wù)場(chǎng)景時(shí)才能快速遷移。3.1 Agent 的認(rèn)知架構(gòu)規(guī)劃、記憶、工具、反思一個(gè)完整的 Agent 系統(tǒng)通常包含四個(gè)核心模塊第一個(gè)是規(guī)劃模塊。Agent 接收用戶目標(biāo)后需要把大目標(biāo)拆解成一個(gè)個(gè)可執(zhí)行的小步驟。比如“幫我寫一篇周報(bào)”Agent 需要規(guī)劃出“收集本周工作內(nèi)容 - 整理成結(jié)構(gòu)化文本 - 生成周報(bào)文件”這樣的步驟。第二個(gè)是記憶模塊。Agent 需要記住用戶的歷史偏好、前幾步的執(zhí)行結(jié)果、已經(jīng)調(diào)用了哪些工具。記憶分短期和長(zhǎng)期短期記憶通常指當(dāng)前會(huì)話的上下文長(zhǎng)期記憶則會(huì)把重要信息持久化存儲(chǔ)比如用戶的稱呼、項(xiàng)目偏好、歷史決策等。第三個(gè)是工具模塊。工具是 Agent 與外部世界交互的通道包括搜索引擎、數(shù)據(jù)庫(kù)查詢接口、企業(yè)內(nèi)部 API、代碼解釋器等。工具定義的清晰程度直接決定 Agent 調(diào)用工具的準(zhǔn)確率。第四個(gè)是反思模塊。高級(jí) Agent 在拿到工具返回結(jié)果后不是簡(jiǎn)單拼進(jìn)上下文就結(jié)束而是會(huì)“檢查結(jié)果是否合理”“是否需要補(bǔ)充信息”“當(dāng)前是否完成用戶目標(biāo)”。這個(gè)環(huán)節(jié)能顯著提高復(fù)雜任務(wù)的完成質(zhì)量。3.2 ReAct 模式推理 行動(dòng)ReAct 是 “Reason Act” 的組合是目前 Agent 最主流的任務(wù)執(zhí)行模式之一。它的核心思路是模型在每一步交替輸出兩種內(nèi)容。第一種是 Thought也就是推理過程解釋“我為什么要做這一步”。第二種是 Action也就是具體行動(dòng)比如“調(diào)用天氣查詢工具參數(shù)是北京”。工具返回結(jié)果后模型再基于結(jié)果繼續(xù)推理直到認(rèn)為任務(wù)完成輸出 Final Answer。為什么要這么做因?yàn)槿绻P椭苯虞敵龃鸢负苋菀壮霈F(xiàn)“幻覺”尤其當(dāng)任務(wù)需要多步計(jì)算或多源信息組合時(shí)一步到位幾乎不可能。而 ReAct 模式通過“推理 - 行動(dòng) - 觀察 - 再推理”的循環(huán)讓模型每一步都有據(jù)可依結(jié)果更可控、可追蹤。3.3 工具調(diào)用的本質(zhì)給模型一個(gè)函數(shù)清單大模型本身不能直接調(diào)用函數(shù)。function calling 的本質(zhì)是我們定義一組函數(shù)的名稱、參數(shù)和描述把它作為“可調(diào)用工具清單”傳給模型。模型根據(jù)用戶輸入在自己的知識(shí)范圍內(nèi)“選擇”合適的函數(shù)并生成調(diào)用參數(shù)然后由我們自己的代碼執(zhí)行這個(gè)函數(shù)。這里有一個(gè)很關(guān)鍵的認(rèn)知模型不執(zhí)行函數(shù)模型只負(fù)責(zé)“決定調(diào)用哪個(gè)函數(shù)、傳什么參數(shù)”。真正執(zhí)行的是你的 Python 代碼。這種設(shè)計(jì)把“決策”和“執(zhí)行”分離開讓系統(tǒng)更安全——你可以在執(zhí)行層做參數(shù)校驗(yàn)、權(quán)限控制、日志記錄。3.4 記憶管理上下文窗口是稀缺資源大模型的上下文窗口有限而 Agent 在多輪交互中會(huì)產(chǎn)生大量中間結(jié)果。如果不做記憶管理Token 很快會(huì)耗盡。常見的記憶管理策略有滑動(dòng)窗口只保留最近 N 輪對(duì)話摘要壓縮把早期對(duì)話用模型生成摘要替代原始文本向量檢索把歷史消息向量化存儲(chǔ)需要時(shí)檢索相關(guān)片段結(jié)構(gòu)化記憶把用戶偏好、任務(wù)狀態(tài)等用結(jié)構(gòu)化字段存儲(chǔ)不占上下文。在實(shí)際項(xiàng)目中通常會(huì)組合使用這些策略。短期對(duì)話用滑動(dòng)窗口長(zhǎng)期偏好用持久化存儲(chǔ)重要知識(shí)用向量庫(kù)。4. 完整實(shí)戰(zhàn)實(shí)現(xiàn)一個(gè)可運(yùn)行的 Agent下面我們來實(shí)現(xiàn)一個(gè)完整的 Agent。為了讓示例容易理解我設(shè)計(jì)了兩個(gè)工具一個(gè)是“獲取城市天氣”的模擬工具一個(gè)是“簡(jiǎn)單計(jì)算器”。Agent 會(huì)根據(jù)用戶問題決定調(diào)用哪個(gè)工具并基于工具返回結(jié)果生成最終回答。4.1 創(chuàng)建項(xiàng)目結(jié)構(gòu)在本地新建一個(gè)項(xiàng)目目錄mkdir ai-agent-tutorial cd ai-agent-tutorial項(xiàng)目結(jié)構(gòu)如下ai-agent-tutorial/ ├── .env ├── tools.py ├── agent.py └── main.pytools.py定義 Agent 可使用的工具函數(shù)agent.py實(shí)現(xiàn) Agent 的主循環(huán)main.py入口腳本負(fù)責(zé)交互。4.2 定義工具函數(shù)工具函數(shù)是 Agent 的執(zhí)行層需要定義成普通 Python 函數(shù)并用一個(gè)統(tǒng)一的“工具清單”描述給模型。# 文件路徑tools.py import random def get_weather(city: str) - str: 獲取指定城市的天氣信息。 實(shí)際項(xiàng)目可以替換為真實(shí)天氣 API。 # 這里使用模擬數(shù)據(jù)真實(shí)場(chǎng)景可改為請(qǐng)求第三方接口 weather_data { 北京: 晴氣溫 18~27 度風(fēng)力 3 級(jí), 上海: 小雨氣溫 22~29 度風(fēng)力 2 級(jí), 廣州: 多云氣溫 25~33 度風(fēng)力 2 級(jí), 深圳: 陣雨氣溫 24~31 度風(fēng)力 3 級(jí), } result weather_data.get(city) if result: return f{city} 的天氣是{result} return f抱歉暫時(shí)沒有 {city} 的天氣數(shù)據(jù)請(qǐng)檢查城市名稱。 def calculator(expression: str) - str: 計(jì)算簡(jiǎn)單的數(shù)學(xué)表達(dá)式例如 1 2 * 3。 注意出于安全考慮這里只支持?jǐn)?shù)字和 - * / 運(yùn)算符。 allowed_chars set(0123456789-*/ ().) if not all(char in allowed_chars for char in expression): return 表達(dá)式中包含非法字符只支持?jǐn)?shù)字和 - * / 運(yùn)算符。 try: result eval(expression, {__builtins__: {}}, {}) return f{expression} 的計(jì)算結(jié)果是{result} except Exception as e: return f計(jì)算失敗{str(e)}解釋一下這段代碼的幾個(gè)設(shè)計(jì)點(diǎn)。get_weather在真實(shí)項(xiàng)目中會(huì)替換成第三方天氣 API 調(diào)用這里用靜態(tài)數(shù)據(jù)是為了讓示例開箱即用。calculator里我特意做了字符白名單校驗(yàn)和eval環(huán)境隔離。這是因?yàn)樵趯?shí)際項(xiàng)目中Agent 生成的參數(shù)如果直接傳給eval會(huì)產(chǎn)生代碼注入風(fēng)險(xiǎn)。這里強(qiáng)調(diào)一個(gè)原則Agent 的工具執(zhí)行層必須做輸入校驗(yàn)和安全兜底不能盲目相信模型生成的參數(shù)。4.3 定義工具清單為了讓模型知道有哪些工具可用我們需要把工具函數(shù)轉(zhuǎn)化成 OpenAI function calling 所需的 JSON 描述格式。# 文件路徑tools.py from typing import List, Dict TOOL_DESCRIPTIONS: List[Dict] [ { type: function, function: { name: get_weather, description: 獲取指定城市的天氣信息輸入城市中文名稱例如‘北京’。, parameters: { type: object, properties: { city: { type: string, description: 城市名稱如‘北京’、‘上海’。 } }, required: [city] } } }, { type: function, function: { name: calculator, description: 計(jì)算簡(jiǎn)單數(shù)學(xué)表達(dá)式支持加、減、乘、除和括號(hào)。, parameters: { type: object, properties: { expression: { type: string, description: 數(shù)學(xué)表達(dá)式例如‘1 2 * 3’。 } }, required: [expression] } } } ] TOOL_MAPPING { get_weather: get_weather, calculator: calculator, }TOOL_DESCRIPTIONS是給模型看的TOOL_MAPPING是給我們自己代碼用的。模型返回工具名和參數(shù)后我們從TOOL_MAPPING中找到對(duì)應(yīng)函數(shù)并執(zhí)行。4.4 實(shí)現(xiàn) Agent 主循環(huán)Agent 主循環(huán)是整個(gè)示例的核心邏輯如下把用戶消息和工具清單一起發(fā)送給模型如果模型返回的是工具調(diào)用消息執(zhí)行對(duì)應(yīng)工具把工具的返回結(jié)果追加到消息列表中再次發(fā)送給模型如果模型返回的是最終回答循環(huán)結(jié)束。# 文件路徑agent.py import os import json from openai import OpenAI from tools import TOOL_DESCRIPTIONS, TOOL_MAPPING client OpenAI( api_keyos.getenv(OPENAI_API_KEY), base_urlos.getenv(OPENAI_BASE_URL), ) def run_agent(user_input: str, max_iterations: int 5) - str: messages [ { role: system, content: 你是一個(gè)智能助手。當(dāng)需要查詢天氣時(shí)使用 get_weather 工具 當(dāng)需要計(jì)算數(shù)學(xué)表達(dá)式時(shí)使用 calculator 工具。 工具執(zhí)行完成后請(qǐng)基于結(jié)果給出簡(jiǎn)潔的最終回答。 }, { role: user, content: user_input, }, ] for _ in range(max_iterations): response client.chat.completions.create( modelos.getenv(MODEL_NAME, gpt-4o-mini), messagesmessages, toolsTOOL_DESCRIPTIONS, tool_choiceauto, ) assistant_message response.choices[0].message if assistant_message.tool_calls: # 1. 先把 assistant 的消息追加到歷史中 messages.append(assistant_message) # 2. 依次執(zhí)行每個(gè)工具調(diào)用 for tool_call in assistant_message.tool_calls: tool_name tool_call.function.name arguments json.loads(tool_call.function.arguments) print(f[Agent 調(diào)用工具] {tool_name}({arguments})) if tool_name not in TOOL_MAPPING: result f未找到工具: {tool_name} else: result TOOL_MAPPING[tool_name](**arguments) # 3. 把工具結(jié)果作為 roletool 的消息追加 messages.append({ role: tool, tool_call_id: tool_call.id, content: str(result), }) else: # 模型沒有要求調(diào)用工具說明任務(wù)完成 return assistant_message.content return 已達(dá)最大迭代次數(shù)任務(wù)未能完成。請(qǐng)簡(jiǎn)化問題或檢查工具定義。這段代碼有幾個(gè)細(xì)節(jié)需要注意。第一messages.append(assistant_message)時(shí)assistant_message本身是一個(gè) Pydantic 對(duì)象新版 openai SDK 支持直接追加到消息列表。如果版本較老可能需要用assistant_message.model_dump()轉(zhuǎn)成字典。第二工具執(zhí)行結(jié)果必須帶上tool_call_id這個(gè) ID 是模型生成工具調(diào)用時(shí)返回的用來把工具結(jié)果和對(duì)應(yīng)的調(diào)用關(guān)聯(lián)起來。第三max_iterations是防止 Agent 進(jìn)入死循環(huán)的保護(hù)機(jī)制。實(shí)際項(xiàng)目中這是必須的因?yàn)槟P陀锌赡芊磸?fù)調(diào)用同一個(gè)工具而始終不收斂。4.5 編寫入口腳本# 文件路徑main.py from dotenv import load_dotenv from agent import run_agent load_dotenv() if __name__ __main__: while True: user_input input(請(qǐng)輸入你的問題輸入 exit 退出) if user_input.strip().lower() exit: break answer run_agent(user_input) print(f\n[最終回答] {answer}\n)4.6 運(yùn)行與驗(yàn)證在項(xiàng)目根目錄執(zhí)行python main.py然后依次輸入幾個(gè)測(cè)試問題請(qǐng)輸入你的問題輸入 exit 退出北京明天適合出行嗎你可以看到類似下面的輸出[Agent 調(diào)用工具] get_weather({city: 北京}) [最終回答] 北京天氣晴朗氣溫在 18~27 度之間風(fēng)力不大比較適合出行外出注意防曬。再測(cè)試數(shù)學(xué)計(jì)算請(qǐng)輸入你的問題輸入 exit 退出幫我算一下 (12 34) * 5 等于多少輸出[Agent 調(diào)用工具] calculator({expression: (12 34) * 5}) [最終回答] (12 34) * 5 的計(jì)算結(jié)果是230。到這里一個(gè)最小可運(yùn)行的 Agent 就完成了。這個(gè)示例雖然簡(jiǎn)單但它體現(xiàn)了 Agent 的完整閉環(huán)理解意圖 - 選擇工具 - 執(zhí)行工具 - 基于結(jié)果作答。5. 常見問題與排查思路Agent 開發(fā)和普通后端開發(fā)的最大區(qū)別是Agent 的行為由模型決定而模型的行為存在概率性。所以排查問題時(shí)除了看代碼邏輯還要學(xué)會(huì)看模型“怎么想”。5.1 高頻問題清單問題現(xiàn)象常見原因解決思路模型不調(diào)用工具直接編造答案工具描述不清晰或系統(tǒng)提示詞沒說明何時(shí)調(diào)用強(qiáng)化工具描述在 system prompt 中明確“必須先調(diào)用工具再回答”工具參數(shù)格式錯(cuò)誤工具 schema 定義不嚴(yán)謹(jǐn)缺示例在參數(shù) description 中補(bǔ)充示例如“城市名稱例如‘北京’”Agent 陷入死循環(huán)工具返回結(jié)果無法讓模型判斷任務(wù)完成增加 max_iterations 保護(hù)讓工具返回更明確的成功/失敗標(biāo)記上下文越來越長(zhǎng)請(qǐng)求報(bào)錯(cuò)沒有清理工具中間結(jié)果對(duì)長(zhǎng)任務(wù)做摘要壓縮或限制工具調(diào)用輪數(shù)工具執(zhí)行報(bào)錯(cuò)模型不返回最終回答工具異常沒有轉(zhuǎn)換為友好消息在工具函數(shù)內(nèi)部捕獲異常返回結(jié)構(gòu)化錯(cuò)誤信息模型調(diào)用了不存在的工具工具清單與執(zhí)行映射不一致統(tǒng)一使用 TOOL_MAPPING 注冊(cè)啟動(dòng)時(shí)做一致性校驗(yàn)5.2 典型問題模型不調(diào)用工具這是入門 Agent 開發(fā)時(shí)最常見的問題。你發(fā)現(xiàn)模型明明可以查天氣但它偏偏自己回答“北京明天晴轉(zhuǎn)多云”數(shù)據(jù)是編的。排查思路如下。第一步檢查工具描述是否清晰。如果描述寫的是“天氣查詢”模型可能不知道應(yīng)該用這個(gè)工具來回答“北京明天適合出行嗎”這類問題。改進(jìn)方式是把描述改成“獲取指定城市的當(dāng)前天氣和未來天氣預(yù)報(bào)適用于出行建議、穿衣建議、活動(dòng)安排等場(chǎng)景”。第二步檢查系統(tǒng)提示詞。要在 system prompt 中明確工具的使用邊界。例如“當(dāng)用戶的問題涉及實(shí)時(shí)數(shù)據(jù)包括天氣、新聞、計(jì)算等你必須先調(diào)用對(duì)應(yīng)工具禁止直接編造數(shù)據(jù)?!钡谌接^察模型的中間思考。如果你使用的是支持日志的模型網(wǎng)關(guān)可以打開請(qǐng)求日志看看模型最終有沒有在 message 中輸出 tool_calls 字段。沒有輸出說明模型根本沒打算調(diào)用工具問題出在提示詞或工具描述有輸出但格式錯(cuò)誤問題出在 schema。5.3 典型問題工具返回結(jié)果不可信工具返回結(jié)果也不是 100% 可信的尤其是調(diào)用第三方 API 時(shí)。天氣接口可能返回“connection timeout”數(shù)據(jù)庫(kù)查詢可能返回空結(jié)果。工程上建議讓工具函數(shù)返回結(jié)構(gòu)化結(jié)果例如{success: True, data: {city: 北京, weather: 晴}}或者{success: False, error: API 請(qǐng)求超時(shí)請(qǐng)稍后重試}這樣模型更容易理解“工具到底成功了沒有”。如果工具返回的是亂碼或者直接拋出異常模型往往不知道該怎么處理最終要么報(bào)錯(cuò)要么編一個(gè)答案。6. AI Agent 工程實(shí)踐與最佳實(shí)踐把 Demo 跑通很容易但要把 Agent 應(yīng)用到生產(chǎn)環(huán)境還需要考慮一系列工程問題。以下是我在實(shí)際項(xiàng)目中總結(jié)的幾條經(jīng)驗(yàn)。6.1 先把 Agent 流程可視化Agent 和傳統(tǒng)程序的差異在于不可控性。上線前建議把 Agent 的決策過程完整記錄下來包括每一步模型用了哪個(gè)工具傳入的參數(shù)是什么工具返回了什么模型最終的回答是什么。這些日志不僅用于排查問題也是后續(xù)優(yōu)化提示詞、評(píng)測(cè)模型效果的重要依據(jù)。具體實(shí)現(xiàn)上可以在run_agent中加入結(jié)構(gòu)化日志print(json.dumps({ tool_name: tool_name, arguments: arguments, result: result, }, ensure_asciiFalse))生產(chǎn)環(huán)境可以改成輸出到日志平臺(tái)或?qū)懭霐?shù)據(jù)庫(kù)。6.2 工具是 Agent 的安全邊界前面寫計(jì)算器工具時(shí)我已經(jīng)強(qiáng)調(diào)了輸入校驗(yàn)。這里再展開說一下。Agent 的工具執(zhí)行層本質(zhì)上是“由模型生成的參數(shù)去驅(qū)動(dòng)你的業(yè)務(wù)代碼”。如果業(yè)務(wù)代碼里有刪除操作、寫操作、支付操作模型一旦被誘導(dǎo)生成惡意參數(shù)后果會(huì)很嚴(yán)重。建議遵循以下原則只暴露最小必要參數(shù)不要直接把整個(gè)請(qǐng)求對(duì)象傳給業(yè)務(wù)代碼對(duì)參數(shù)做白名單校驗(yàn)尤其是命令執(zhí)行、文件讀寫、數(shù)據(jù)庫(kù)操作高風(fēng)險(xiǎn)操作需要二次確認(rèn)例如“刪除”類操作讓用戶確認(rèn)后再執(zhí)行記錄誰(shuí)在什么時(shí)間、通過哪個(gè) Agent 會(huì)話觸發(fā)了哪些操作。6.3 控制成本與延遲Agent 的多輪調(diào)用意味著多次模型請(qǐng)求而每個(gè)工具結(jié)果回填后還要再次請(qǐng)求模型成本和時(shí)間會(huì)成倍增長(zhǎng)。優(yōu)化手段主要有幾個(gè)方向。第一精簡(jiǎn)上下文。優(yōu)先只保留當(dāng)前任務(wù)相關(guān)的歷史消息工具返回結(jié)果超出一定長(zhǎng)度時(shí)用摘要替代原文。第二模型分級(jí)。簡(jiǎn)單任務(wù)用小模型復(fù)雜規(guī)劃用大模型。例如文本分類、實(shí)體抽取這類步驟用小模型最終答案生成用大模型。第三緩存工具結(jié)果。同一個(gè)城市、同一個(gè)時(shí)間段的天氣查詢結(jié)果可以緩存一段時(shí)間避免重復(fù)調(diào)用。6.4 評(píng)測(cè)驅(qū)動(dòng)迭代Agent 的效果優(yōu)化不能靠“感覺”。建議建立一套評(píng)測(cè)集比如 50 條典型用戶問題每條標(biāo)注期望的工具調(diào)用順序和最終回答要點(diǎn)。每次修改提示詞、工具定義或模型版本都跑一遍評(píng)測(cè)集記錄通過率。這樣做的好處是你能明確知道這次改動(dòng)到底是變好了還是變差了。評(píng)測(cè)集可以設(shè)計(jì)成表格用戶問題期望工具期望回答要點(diǎn)實(shí)際是否達(dá)標(biāo)北京明天適合出行嗎get_weather基于天氣數(shù)據(jù)給出建議是/否計(jì)算 3*72calculator結(jié)果為 23是/否6.5 多 Agent 協(xié)作是后續(xù)方向當(dāng)一個(gè) Agent 承擔(dān)的職責(zé)過多時(shí)提示詞會(huì)變得臃腫工具數(shù)量暴增模型的選擇準(zhǔn)確率也會(huì)下降。更合理的架構(gòu)是多個(gè)專業(yè) Agent 協(xié)作每個(gè) Agent 只負(fù)責(zé)一個(gè)領(lǐng)域由一個(gè)“調(diào)度 Agent”統(tǒng)一規(guī)劃任務(wù)。例如一個(gè)客服系統(tǒng)中的 Agent 可以拆分為訂單查詢 Agent物流查詢 Agent售后服務(wù) Agent優(yōu)惠計(jì)算 Agent。調(diào)度 Agent 根據(jù)用戶問題選擇交給哪個(gè)子 Agent。這樣每個(gè)子 Agent 的工具集更精簡(jiǎn)提示詞更聚焦整體效果通常更好。7. 總結(jié)與下一步學(xué)習(xí)路線回到最開始說的那本書??型辍渡钊肜斫?AI Agent設(shè)計(jì)原理與工程實(shí)踐》這類書最重要的收獲不是記住了幾個(gè)框架的名字而是建立起對(duì) Agent 系統(tǒng)整體的認(rèn)知框架規(guī)劃、記憶、工具、反思外加工程上的穩(wěn)定性、安全性和可觀測(cè)性。如果你正在學(xué) Agent 開發(fā)下面這條路線可以作為參考。第一步把本文的示例代碼跑起來修改工具函數(shù)和提示詞感受模型調(diào)用工具的完整流程。第二步閱讀 ReAct 論文原文理解“推理 - 行動(dòng) - 觀察”的循環(huán)為什么有效。第三步嘗試接入一個(gè)真實(shí)的外部 API比如天氣 API、新聞 API把靜態(tài)工具替換成真實(shí)請(qǐng)求。第四步研究 LangChain、LlamaIndex 這類框架的 Agent 實(shí)現(xiàn)源碼搞清楚它們封裝了哪些能力隱藏了哪些細(xì)節(jié)。第五步挑戰(zhàn)復(fù)雜業(yè)務(wù)場(chǎng)景比如多表格問答、多步驟數(shù)據(jù)加工、多 Agent 協(xié)作重點(diǎn)關(guān)注上下文的控制、工具結(jié)果的校驗(yàn)和異?;謴?fù)。最后再提醒一句Agent 的工程化難度不取決于模型有多強(qiáng)而取決于你對(duì)邊界條件的處理有多細(xì)致??梢韵葟囊粋€(gè)小場(chǎng)景開始把閉環(huán)跑通再逐步擴(kuò)大應(yīng)用范圍這是最穩(wěn)妥的成長(zhǎng)路徑。