用 Kimi K3 跑代码 Agent:工具调用、长程任务与整库重构
Kimi K3 擅长长程编程与 Agent。教你用 tools 做函数调用、tool_choice 强制调用、把工具定义放进 system 动态加载,以及多轮里为何必须原样回传完整 assistant message,附整库重构实战。
Kimi K3 官方定位里排第一的就是「长程编程」—— 1M 上下文装得下整个仓库,常开推理扛得住多步规划,原生工具调用能驱动终端和外部函数。这让它很适合做代码 Agent:自己读代码、调工具、跑一长串动作把任务做完。这篇讲清楚怎么用 K3 的工具调用把 Agent 搭起来,以及长程任务里最容易踩的那个坑。
工具调用(function calling)基础
K3 兼容 OpenAI 的 tools 规范,定义一个工具、让模型自己决定何时调用:
import os, json
from openai import OpenAI
client = OpenAI(api_key=os.environ["MOONSHOT_API_KEY"],
base_url="https://api.moonshot.cn/v1")
tools = [{
"type": "function",
"function": {
"name": "read_file",
"description": "读取仓库里某个文件的内容",
"parameters": {
"type": "object",
"properties": {"path": {"type": "string"}},
"required": ["path"],
},
},
}]
messages = [{"role": "user", "content": "看看 auth.py 里有没有硬编码的密钥"}]
resp = client.chat.completions.create(
model="kimi-k3", messages=messages, tools=tools,
)
当模型决定调用工具,返回的 assistant 消息里会带 tool_calls;你在本地执行对应函数,把结果作为 role:"tool" 消息接回去,再请求下一轮。
关键坑:多轮里必须原样回传完整 assistant message
这是从 K2 迁移过来的人最容易翻车的地方:多轮对话和工具调用时,要把 API 返回的完整 assistant message 原样加进下一次请求,不要只保留 content。
K3 常开推理,assistant 消息里除了 content 还携带推理 / 工具状态,只回传 content 会让模型「失忆」,推理链断掉、工具调用错乱。正确写法:
# 把整条 assistant 消息(含 tool_calls / 推理状态)原样 append
messages.append(resp.choices[0].message)
# 执行工具,把结果作为 tool 消息接回
for call in resp.choices[0].message.tool_calls or []:
result = run_tool(call.function.name, json.loads(call.function.arguments))
messages.append({
"role": "tool",
"tool_call_id": call.id,
"content": json.dumps(result),
})
# 带着完整历史请求下一轮
resp = client.chat.completions.create(
model="kimi-k3", messages=messages, tools=tools,
)
记住:append 整个 message 对象,而不是自己重新拼一个只有 content 的。
强制调用与动态加载工具
- 强制调用:想让模型这一轮必须用工具,设
tool_choice="required"(或指定具体某个函数),适合「必须先查再答」的流程。 - 动态加载工具:工具很多时,可以把工具定义放进 system 消息里按需给出,而不是每轮都塞满
tools数组,省上下文也更灵活。 - 官方工具:月之暗面还提供了一批内置工具能力,通过官方的
/tools、/fibers等端点接入,细节以官方文档为准。
长程任务为什么适合 K3
一个跑很多轮的代码 Agent,上下文会越滚越长:仓库内容 + 一轮轮工具结果 + 推理历史。K3 的两个特性正好接住:
- 1M 上下文装得下整库 + 长历史,不会中途因为超限而丢上下文(长上下文组织见 1M 上下文指南);
- 默认缓存让不变的前缀(仓库、system、工具定义)反复命中,把长程 Agent 的输入成本压到 ¥2/M —— 否则一轮轮重发前缀会很贵(算账见 K3 价格详解)。
所以组织消息时,把仓库内容和工具定义尽量前置、保持稳定,让缓存吃满;每轮变化的只追加在后面。
整库重构实战思路
一个典型的「整库重构」Agent 循环:
- 喂全貌:把仓库(或 RAG 检索到的相关部分)+ system 指令一次性放进上下文;
- 让它规划:先让 K3 输出重构计划(改哪些文件、风险点),常开推理在这步价值最大;
- 带工具执行:开
read_file/write_file/run_tests等工具,让它一步步改、跑测试; - 原样回传:每轮把完整 assistant message + tool 结果接回,维持推理链;
- 收尾核查:让它对照初始计划自检有没有漏改、测试是否全绿。
这套流程也可以直接架在聚合网关上,把规划交给 K3、把某些子任务分流给 Claude Opus 等模型(横评见 K3 vs Claude vs GPT),都在一个 Key 下完成。
小结
K3 做代码 Agent 的核心心法就三条:tools 驱动动作、缓存 + 前置压成本、多轮原样回传完整 assistant message。踩对这三点,长程任务就能稳定跑下来。完整接入与报错排查见 Kimi K3 API 接入教程。想用一个 Key 在 K3 和别家模型间自由分流,从 GetModel 控制台开始。