用 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 循环:

  1. 喂全貌:把仓库(或 RAG 检索到的相关部分)+ system 指令一次性放进上下文;
  2. 让它规划:先让 K3 输出重构计划(改哪些文件、风险点),常开推理在这步价值最大;
  3. 带工具执行:开 read_file / write_file / run_tests 等工具,让它一步步改、跑测试;
  4. 原样回传:每轮把完整 assistant message + tool 结果接回,维持推理链;
  5. 收尾核查:让它对照初始计划自检有没有漏改、测试是否全绿。

这套流程也可以直接架在聚合网关上,把规划交给 K3、把某些子任务分流给 Claude Opus 等模型(横评见 K3 vs Claude vs GPT),都在一个 Key 下完成。

小结

K3 做代码 Agent 的核心心法就三条:tools 驱动动作、缓存 + 前置压成本、多轮原样回传完整 assistant message。踩对这三点,长程任务就能稳定跑下来。完整接入与报错排查见 Kimi K3 API 接入教程。想用一个 Key 在 K3 和别家模型间自由分流,从 GetModel 控制台开始。