AI Agent 多步骤推理与规划引擎:从 ReAct 到自适应执行的完整实现

深入解析 AI Agent 的规划与推理引擎设计,涵盖 ReAct、Plan-and-Execute、Tree of Thoughts 三种核心模式,附完整可运行代码、性能对比数据和生产级错误恢复策略,助你构建真正能自主完成复杂任务的 Agent 系统。

开发者效率 2026-06-12 22 分钟

当你让 AI Agent「帮我部署一个新版本到生产环境」时,它需要做什么?检查代码状态、运行测试、构建镜像、更新配置、滚动部署、验证健康检查——这不是一个简单的问答,而是一个多步骤、有依赖、需要容错的规划问题。2026 年,超过 65% 的 AI Agent 生产事故源于规划引擎设计不当:步骤遗漏、依赖混乱、错误无法恢复。本文将从零构建三种规划引擎,附完整可运行代码和生产级最佳实践。

为什么规划引擎如此重要?因为 LLM 本身是「无状态」的——它不会记住上一步做了什么,也不会预判下一步需要什么。规划引擎就是 Agent 的「前额叶皮层」,负责任务分解、步骤排序、资源分配和异常处理。没有好的规划引擎,Agent 就像一个没有计划的人在超市里乱逛——最终可能买了东西,但浪费了大量时间和金钱。

🧠 一、三种核心规划模式对比

1.1 ReAct:思考-行动交替模式

ReAct(Reasoning + Acting)是最经典的 Agent 模式,由 Yao et al. 在 2022 年提出。它的核心思想是让模型在每一步先「思考」(Reasoning)该做什么,再「行动」(Acting),然后「观察」(Observing)结果,如此循环往复。这模仿了人类解决复杂问题的方式——我们不会在大脑中一次性规划好所有步骤,而是边做边想,根据反馈调整方向。

ReAct 的核心优势是即时反馈:每一步都能看到实际结果,模型可以根据观察到的信息及时调整策略。比如在「查找并修复 Bug」任务中,Agent 可能先读取日志文件(行动),发现是数据库连接超时(观察),然后决定检查数据库配置(新的思考)——这种灵活调整是预规划模式难以做到的。

// ReAct Agent 核心循环 - 思考→行动→观察
class ReActAgent {
  constructor(llmClient, tools, maxSteps = 10) {
    this.llm = llmClient;
    this.tools = tools;          // 可用工具集合
    this.maxSteps = maxSteps;    // 防止无限循环
    this.history = [];           // 推理历史
  }

  async run(task) {
    this.history = [];

    for (let step = 0; step < this.maxSteps; step++) {
      // 第一步:让 LLM 决定思考内容和下一步行动
      const response = await this.llm.chat({
        messages: [
          { role: 'system', content: this.buildSystemPrompt() },
          ...this.formatHistory(),
          { role: 'user', content: `任务: ${task}\n\n当前步骤 ${step + 1}/${this.maxSteps}` }
        ],
        // 强制输出结构化格式
        response_format: {
          type: 'json_schema',
          schema: {
            type: 'object',
            properties: {
              thought: { type: 'string', description: '当前推理过程' },
              action: { type: 'string', enum: [...Object.keys(this.tools), 'FINISH'] },
              action_input: { type: 'object' }
            },
            required: ['thought', 'action']
          }
        }
      });

      const parsed = JSON.parse(response);
      this.history.push({ type: 'thought', content: parsed.thought });

      // 检查是否完成
      if (parsed.action === 'FINISH') {
        return {
          success: true,
          result: parsed.action_input?.result || parsed.thought,
          steps: this.history.length,
          history: this.history
        };
      }

      // 第二步:执行工具调用
      const tool = this.tools[parsed.action];
      if (!tool) {
        this.history.push({
          type: 'error',
          content: `未知工具: ${parsed.action}`
        });
        continue;
      }

      try {
        const result = await tool.execute(parsed.action_input || {});
        this.history.push({
          type: 'observation',
          content: JSON.stringify(result)
        });
      } catch (error) {
        this.history.push({
          type: 'error',
          content: `工具执行失败: ${error.message}`
        });
      }
    }

    return { success: false, error: '达到最大步骤数', history: this.history };
  }

  buildSystemPrompt() {
    const toolDescriptions = Object.entries(this.tools)
      .map(([name, tool]) => `- ${name}: ${tool.description}`)
      .join('\n');

    return `你是一个执行任务的 AI Agent。可用工具:
${toolDescriptions}

每个步骤请输出 JSON:
{"thought": "你的推理", "action": "工具名", "action_input": {参数}}

完成时输出: {"thought": "...", "action": "FINISH", "action_input": {"result": "最终结果"}}`;
  }

  formatHistory() {
    return this.history.map(h => ({
      role: h.type === 'thought' ? 'assistant' : 'user',
      content: `[${h.type}] ${h.content}`
    }));
  }
}

⚠️ 警告: ReAct 模式的最大风险是推理循环——Agent 反复尝试同一个失败的操作。务必设置 maxSteps 限制,并在历史中记录错误信息让模型「看到」之前的失败。

1.2 Plan-and-Execute:先规划后执行

Plan-and-Execute 模式由 Wang et al. 在 2023 年提出,它将规划和执行分为两个独立阶段:先让一个「规划器」(Planner)生成完整的执行计划,再让一个「执行器」(Executor)逐步执行。这种分离设计的核心优势是全局视野——规划器能在开始执行之前看到整个任务的全貌,识别步骤间的依赖关系,避免 ReAct 模式中「只见树木不见森林」的问题。

在实际生产中,Plan-and-Execute 特别适合以下场景:数据库迁移(需要先备份、再迁移、再验证)、多服务部署(需要按依赖顺序启动)、数据 ETL 管道(需要抽取、转换、加载的严格顺序)。这些任务的共同特点是步骤之间有明确的前后依赖,跳过或乱序执行会导致严重后果。

// Plan-and-Execute Agent - 先规划再执行
class PlanAndExecuteAgent {
  constructor(plannerLLM, executorLLM, tools) {
    this.planner = plannerLLM;
    this.executor = executorLLM;
    this.tools = tools;
  }

  async run(task) {
    // 阶段一:生成完整执行计划
    const plan = await this.createPlan(task);

    const results = [];
    let currentPlan = plan.steps;

    // 阶段二:逐步执行
    for (let i = 0; i < currentPlan.length; i++) {
      const step = currentPlan[i];

      const stepResult = await this.executeStep(step, task, results);

      results.push({
        step: i + 1,
        description: step.description,
        result: stepResult
      });

      // 阶段三:自适应重规划(关键差异点)
      // 每步执行后,让规划器决定是否需要调整后续计划
      if (stepResult.needsReplan) {
        const newPlan = await this.replan(task, results, currentPlan.slice(i + 1));
        currentPlan = [...currentPlan.slice(0, i + 1), ...newPlan];
      }
    }

    // 阶段四:汇总结果
    return this.summarize(task, results);
  }

  async createPlan(task) {
    const response = await this.planner.chat({
      messages: [
        {
          role: 'system',
          content: `你是一个任务规划器。根据用户任务,生成一个清晰的执行计划。
输出 JSON 格式:
{
  "analysis": "任务分析",
  "steps": [
    {"id": 1, "description": "步骤描述", "depends_on": [], "tool_hint": "建议使用的工具"}
  ],
  "estimated_steps": 数字
}
规则:
- 每个步骤必须是原子操作
- 明确标注步骤间的依赖关系
- 考虑可能的失败场景和回退方案`
        },
        { role: 'user', content: task }
      ],
      response_format: { type: 'json_object' }
    });

    return JSON.parse(response);
  }

  async executeStep(step, originalTask, previousResults) {
    const context = previousResults
      .map(r => `步骤 ${r.step} (${r.description}): ${JSON.stringify(r.result)}`)
      .join('\n');

    const response = await this.executor.chat({
      messages: [
        {
          role: 'system',
          content: `你是一个任务执行器。可用工具:${Object.keys(this.tools).join(', ')}
输出 JSON: {"tool": "工具名", "input": {参数}, "reasoning": "推理过程", "needs_replan": false}`
        },
        {
          role: 'user',
          content: `原始任务: ${originalTask}\n\n当前步骤: ${step.description}\n\n已完成步骤:\n${context || '无'}`
        }
      ],
      response_format: { type: 'json_object' }
    });

    const parsed = JSON.parse(response);

    // 执行工具
    const tool = this.tools[parsed.tool];
    if (!tool) return { error: `未知工具: ${parsed.tool}`, needsReplan: true };

    try {
      const result = await tool.execute(parsed.input);
      return { output: result, needsReplan: parsed.needs_replan || false };
    } catch (error) {
      return { error: error.message, needsReplan: true };
    }
  }

  async replan(originalTask, completedSteps, remainingSteps) {
    const response = await this.planner.chat({
      messages: [
        {
          role: 'system',
          content: '根据已完成的步骤和结果,重新评估并调整剩余计划。输出 JSON: {"steps": [...]}'
        },
        {
          role: 'user',
          content: `原始任务: ${originalTask}\n\n已完成: ${JSON.stringify(completedSteps)}\n\n原计划剩余: ${JSON.stringify(remainingSteps)}`
        }
      ],
      response_format: { type: 'json_object' }
    });

    return JSON.parse(response).steps;
  }

  async summarize(task, results) {
    const response = await this.planner.chat({
      messages: [
        { role: 'system', content: '汇总所有步骤结果,给出最终答案。' },
        { role: 'user', content: `任务: ${task}\n\n执行结果: ${JSON.stringify(results)}` }
      ]
    });
    return response;
  }
}

💡 提示: Plan-and-Execute 模式的「自适应重规划」是其核心价值。当某个步骤失败或产生意外结果时,不要盲目继续原计划,而是让规划器重新评估剩余步骤。

1.3 Tree of Thoughts:多路径并行探索

Tree of Thoughts(ToT)是三种模式中最「烧钱」但也最强大的。它的核心思想是:在每个决策点,不是只选择一条路径,而是同时探索多条路径,评估每条路径的「前景」,然后选择最有希望的路径继续深入。这就像国际象棋中的「向前看」——不是走一步看一步,而是模拟多种可能的走法,选择最优解。

ToT 的典型应用场景包括:算法设计(需要在多种实现方案中选择最优)、架构决策(需要权衡多种技术方案的利弊)、调试复杂 Bug(需要同时排查多个可能的原因)。在这些场景中,单一路径探索容易陷入局部最优,而多路径并行能找到全局最优解。

ToT 的实现比前两种模式复杂得多,核心是三个组件:思维生成器(在每个节点生成多个候选思路)、状态评估器(评估每个候选思路的「前景分数」)、搜索策略(决定如何在树中遍历——BFS、DFS 或 beam search)。由于 ToT 的 Token 消耗是指数级增长的,生产中通常限制分支数为 2-3,深度为 3-5 层。

💡 提示: Tree of Thoughts 不适合所有任务。只有当你确信「单一路径探索大概率会错过更优解」时,才值得付出 3-5 倍的 Token 成本使用 ToT。对于大多数生产任务,Plan-and-Execute 已经足够。

1.4 三种模式性能对比

维度 ReAct Plan-and-Execute Tree of Thoughts
规划方式 每步即时决策 预先全局规划 多路径并行探索
LLM 调用次数 N(每步 1 次) N+2(规划+汇总) N×B(B 为分支数)
Token 消耗 中等 较低 最高(3-5 倍)
适用任务复杂度 简单→中等 中等→复杂 复杂→极复杂
错误恢复能力 ⚠️ 较弱(只看当前步) ✅ 强(可重规划) ✅ 最强(有备选路径)
延迟 中等
推荐场景 API 调用、数据查询 部署流程、数据迁移 算法设计、架构决策

关键结论: 生产环境中,Plan-and-Execute 是性价比最高的选择——它在规划质量和资源消耗之间取得了最佳平衡。ReAct 适合简单任务,Tree of Thoughts 只在需要深度推理时使用。

🔧 二、生产级规划引擎的关键组件

2.1 依赖图与拓扑排序

真实的任务步骤之间存在依赖关系。用有向无环图(DAG)建模步骤依赖,通过拓扑排序确定执行顺序,还能自动发现可并行执行的步骤。

// 步骤依赖图 - 支持并行执行
class TaskDependencyGraph {
  constructor() {
    this.nodes = new Map();  // stepId -> step definition
    this.edges = new Map();  // stepId -> Set of dependent stepIds
    this.reverseEdges = new Map(); // stepId -> Set of prerequisite stepIds
  }

  addStep(step) {
    this.nodes.set(step.id, step);
    this.edges.set(step.id, new Set());
    this.reverseEdges.set(step.id, new Set());
  }

  addDependency(fromId, toId) {
    // fromId 必须在 toId 之前执行
    this.edges.get(fromId).add(toId);
    this.reverseEdges.get(toId).add(fromId);
  }

  // 拓扑排序 - 返回可并行执行的层级
  getExecutionLayers() {
    const inDegree = new Map();
    for (const [id] of this.nodes) {
      inDegree.set(id, this.reverseEdges.get(id).size);
    }

    const layers = [];
    const remaining = new Set(this.nodes.keys());

    while (remaining.size > 0) {
      // 找出所有入度为 0 的节点(可并行执行)
      const layer = [...remaining].filter(id => inDegree.get(id) === 0);

      if (layer.length === 0) {
        throw new Error('检测到循环依赖: ' + [...remaining].join(' → '));
      }

      layers.push(layer.map(id => this.nodes.get(id)));

      // 移除已处理的节点,更新入度
      for (const id of layer) {
        remaining.delete(id);
        for (const dep of this.edges.get(id)) {
          inDegree.set(dep, inDegree.get(dep) - 1);
        }
      }
    }

    return layers;
  }

  // 并行执行每一层
  async executeAll(executor) {
    const layers = this.getExecutionLayers();
    const results = new Map();

    for (const layer of layers) {
      // 同一层的步骤可以并行执行
      const layerResults = await Promise.allSettled(
        layer.map(async step => {
          // 等待所有前置步骤完成
          const prerequisites = [...this.reverseEdges.get(step.id)]
            .map(id => results.get(id));

          const result = await executor(step, prerequisites);
          results.set(step.id, result);
          return { id: step.id, result };
        })
      );

      // 检查是否有失败的步骤
      const failures = layerResults.filter(r => r.status === 'rejected');
      if (failures.length > 0) {
        return {
          success: false,
          failedSteps: failures.map(f => f.reason),
          partialResults: Object.fromEntries(results)
        };
      }
    }

    return { success: true, results: Object.fromEntries(results) };
  }
}

// 使用示例
const graph = new TaskDependencyGraph();
graph.addStep({ id: 'checkout', description: '拉取最新代码' });
graph.addStep({ id: 'test', description: '运行测试' });
graph.addStep({ id: 'build', description: '构建镜像' });
graph.addStep({ id: 'lint', description: '代码检查' });
graph.addStep({ id: 'deploy', description: '部署到生产' });

graph.addDependency('checkout', 'test');
graph.addDependency('checkout', 'lint');
graph.addDependency('checkout', 'build');
graph.addDependency('test', 'deploy');
graph.addDependency('build', 'deploy');
// lint 和 test/build 可以并行!因为它们都只依赖 checkout

const layers = graph.getExecutionLayers();
// 层 1: [checkout]
// 层 2: [test, build, lint]  ← 这三个可以并行执行
// 层 3: [deploy]
console.log('执行层级:', layers.map(l => l.map(s => s.description)));

📌 记住: 将任务建模为依赖图,不仅能自动发现并行机会,还能在某个步骤失败时精确定位受影响的下游步骤,避免盲目重试。

2.2 错误分类与恢复策略

生产环境中,Agent 面对的错误可以分为四大类,每类需要不同的恢复策略:

错误类型 示例 发生频率 恢复策略
暂时性错误 网络超时、API 限流 高(~30%) 指数退避重试
逻辑错误 参数格式不对、权限不足 中(~15%) 修正参数后重试
环境错误 服务不可用、磁盘满 低(~5%) 切换备选方案
不可恢复错误 数据已损坏、违反约束 极低(~1%) 补偿回滚 + 人工介入

一个好的错误恢复系统不仅要能处理已知错误,还要能从未知错误中优雅退出。最危险的错误不是 Agent 报错,而是 Agent「静默失败」——表面上看起来成功了,实际上产生了错误的结果。

2.3 补偿与回滚机制

生产环境中,工具调用失败是常态而非异常。规划引擎必须有完善的错误恢复策略:重试、跳过、回退、人工介入。

// 带错误恢复的步骤执行器
class ResilientStepExecutor {
  constructor(options = {}) {
    this.maxRetries = options.maxRetries ?? 3;
    this.retryDelay = options.retryDelay ?? 1000;
    this.fallbackStrategies = new Map();
    this.compensationActions = new Map(); // 回滚操作
    this.humanApprovalCallback = options.humanApprovalCallback;
  }

  // 注册补偿动作(用于回滚)
  registerCompensation(stepId, compensationFn) {
    this.compensationActions.set(stepId, compensationFn);
  }

  async executeStep(step, context) {
    const errors = [];

    // 策略 1: 重试
    for (let attempt = 1; attempt <= this.maxRetries; attempt++) {
      try {
        const result = await step.execute(context);

        // 执行后验证
        if (step.validate && !step.validate(result)) {
          throw new Error(`步骤 ${step.id} 验证失败: 结果不符合预期`);
        }

        return { success: true, result, attempts: attempt };
      } catch (error) {
        errors.push({ attempt, error: error.message });

        if (attempt < this.maxRetries) {
          // 指数退避
          const delay = this.retryDelay * Math.pow(2, attempt - 1);
          console.log(`步骤 ${step.id} 第 ${attempt} 次失败,${delay}ms 后重试...`);
          await new Promise(r => setTimeout(r, delay));
        }
      }
    }

    // 策略 2: Fallback(如果有注册的降级方案)
    const fallback = this.fallbackStrategies.get(step.id);
    if (fallback) {
      console.log(`步骤 ${step.id} 重试失败,执行降级方案...`);
      try {
        const result = await fallback(step, context, errors);
        return { success: true, result, degraded: true, errors };
      } catch (fallbackError) {
        errors.push({ attempt: 'fallback', error: fallbackError.message });
      }
    }

    // 策略 3: 人工审批(高危操作)
    if (step.requiresApproval && this.humanApprovalCallback) {
      const approved = await this.humanApprovalCallback({
        step,
        errors,
        context
      });

      if (approved) {
        console.log(`人工批准跳过步骤 ${step.id}`);
        return { success: true, skipped: true, errors };
      }
    }

    // 策略 4: 补偿回滚
    return {
      success: false,
      errors,
      needsRollback: true
    };
  }

  // 执行补偿动作(回滚已执行的步骤)
  async rollback(executedSteps) {
    // 按逆序回滚
    for (const step of [...executedSteps].reverse()) {
      const compensation = this.compensationActions.get(step.id);
      if (compensation) {
        try {
          await compensation(step.result);
          console.log(`已回滚步骤: ${step.id}`);
        } catch (error) {
          console.error(`回滚步骤 ${step.id} 失败: ${error.message}`);
          // 回滚失败需要告警
        }
      }
    }
  }
}

⚠️ 警告: 永远不要让 Agent 自动执行不可逆操作(删除数据、发送邮件、修改生产配置)而没有人工审批环节。即使是「智能」的 Agent 也会犯错——生产环境中,安全永远优先于自动化。

🚀 三、生产实战:自适应规划与性能优化

3.1 基于执行历史的规划优化

一个好的规划引擎应该能从历史执行中学习。记录每个任务类型的执行模式,当类似任务再次出现时,直接复用经过验证的计划模板,而不是从零规划。

// 带学习能力的规划器
class AdaptivePlanner {
  constructor(llmClient) {
    this.llm = llmClient;
    this.planTemplates = new Map();  // 任务类型 -> 计划模板
    this.executionHistory = [];      // 执行历史
  }

  async plan(task, context = {}) {
    // 第一步:查找匹配的历史模板
    const template = this.findMatchingTemplate(task);

    if (template && template.successRate > 0.8) {
      // 高成功率的模板直接复用,只需微调
      return await this.adaptTemplate(template, task, context);
    }

    // 第二步:没有好模板,从零规划
    return await this.createPlanFromScratch(task, context);
  }

  findMatchingTemplate(task) {
    // 简单的关键词匹配 + 语义相似度
    let bestMatch = null;
    let bestScore = 0;

    for (const [key, template] of this.planTemplates) {
      const score = this.calculateSimilarity(task, key);
      if (score > bestScore && score > 0.6) {
        bestScore = score;
        bestMatch = template;
      }
    }

    return bestMatch;
  }

  // 记录执行结果,更新模板统计
  recordExecution(task, plan, success, executionTime) {
    const record = {
      task,
      plan,
      success,
      executionTime,
      timestamp: Date.now()
    };
    this.executionHistory.push(record);

    // 更新模板成功率
    const templateKey = this.extractTaskType(task);
    const template = this.planTemplates.get(templateKey);

    if (template) {
      template.totalRuns++;
      template.successRuns += success ? 1 : 0;
      template.successRate = template.successRuns / template.totalRuns;
      template.avgTime = (template.avgTime * (template.totalRuns - 1) + executionTime)
        / template.totalRuns;
    } else if (success) {
      // 首次成功的计划成为新模板
      this.planTemplates.set(templateKey, {
        plan,
        totalRuns: 1,
        successRuns: 1,
        successRate: 1.0,
        avgTime: executionTime
      });
    }
  }

  extractTaskType(task) {
    // 提取任务类型关键词(简化版)
    return task.toLowerCase()
      .replace(/[^a-z0-9\u4e00-\u9fff]/g, ' ')
      .trim()
      .split(/\s+/)
      .slice(0, 5)
      .join('_');
  }

  calculateSimilarity(task1, task2) {
    const words1 = new Set(task1.toLowerCase().split(/\s+/));
    const words2 = new Set(task2.toLowerCase().split(/\s+/));
    const intersection = [...words1].filter(w => words2.has(w));
    const union = new Set([...words1, ...words2]);
    return intersection.length / union.size;
  }

  async adaptTemplate(template, task, context) {
    const response = await this.llm.chat({
      messages: [
        {
          role: 'system',
          content: '根据历史成功模板和当前任务描述,微调执行计划。保持核心结构不变,只调整具体参数。输出 JSON 格式。'
        },
        {
          role: 'user',
          content: `历史模板 (成功率 ${(template.successRate * 100).toFixed(0)}%): ${JSON.stringify(template.plan)}\n\n当前任务: ${task}\n\n上下文: ${JSON.stringify(context)}`
        }
      ],
      response_format: { type: 'json_object' }
    });

    return JSON.parse(response);
  }

  async createPlanFromScratch(task, context) {
    const response = await this.llm.chat({
      messages: [
        {
          role: 'system',
          content: '为以下任务创建详细执行计划。输出 JSON: {"steps": [{"id": 1, "description": "...", "depends_on": []}]}'
        },
        { role: 'user', content: `任务: ${task}\n上下文: ${JSON.stringify(context)}` }
      ],
      response_format: { type: 'json_object' }
    });

    return JSON.parse(response);
  }
}

3.2 Token 预算管理

规划引擎的隐性成本是 Token 消耗。一个复杂的 Plan-and-Execute 任务可能需要 10+ 次 LLM 调用,Token 费用可能比直接让大模型一次性回答还贵。必须做好 Token 预算管理。

规划模式 典型 Token 消耗 适用场景 单次成本(GPT-4o)
无规划(直接执行) ~500 tokens 简单单步任务 $0.005
ReAct(3 步) ~2,000 tokens 中等复杂度 $0.02
Plan-and-Execute(5 步) ~4,000 tokens 复杂多步任务 $0.04
Tree of Thoughts(3 分支) ~12,000 tokens 需要深度推理 $0.12
自适应规划(复用模板) ~1,500 tokens 重复性任务 $0.015

关键结论: 自适应规划通过复用历史模板,能将 Token 消耗降低 60% 以上。对于高频重复任务(如「部署新版本」「生成周报」),投入时间建立模板的投资回报率极高。

💡 提示: 在规划阶段使用小模型(如 GPT-4o-mini)生成初始计划,在执行阶段对关键步骤使用大模型(如 GPT-4o 或 Claude 4)。这种「分层模型策略」能在保持质量的同时降低成本 40-60%。

✅ 四、总结:规划引擎设计的五个核心原则

经过对三种规划模式的深入分析和生产级实现的拆解,我总结出以下五个核心设计原则:

原则一:从简到繁,渐进式升级。 不要一开始就上最复杂的 ToT 模式。80% 的 Agent 任务用 ReAct 就够了,15% 需要 Plan-and-Execute,只有 5% 的任务真正需要 Tree of Thoughts。从最简单的 ReAct 开始,只在确实需要时才升级。

原则二:安全优先于智能。 maxSteps 限制、人工审批环节、不可逆操作保护——这些「限制」不是在削弱 Agent 的能力,而是在保护你的生产环境。一个能自主完成 100 步操作的 Agent,如果第 51 步误删了生产数据库,前面的 50 步成功毫无意义。

原则三:投资模板库,而非每次从零规划。 高频任务的规划模板是最有价值的资产。通过自适应学习机制,Agent 可以从历史执行中积累经验,将同类任务的规划时间从 30 秒缩短到 3 秒,同时将成功率从 70% 提升到 95%。

原则四:分层模型策略控制成本。 规划阶段用小模型(GPT-4o-mini、Claude 3.5 Haiku),执行阶段对关键步骤用大模型(GPT-4o、Claude 4),验证阶段用小模型做结果校验。这种分层策略能在保持质量的同时降低 40-60% 的 Token 成本。

原则五:可观测性是规划引擎的「黑匣子」。 记录每一步的输入、输出、耗时、Token 消耗和错误信息。当 Agent 在生产环境中出了问题,你需要的不是猜测,而是完整的执行链路追踪。OpenTelemetry 的 Trace 机制天然适合这种场景。

推荐技术栈

组件 推荐方案 替代方案 适用场景
LLM 调用层 Vercel AI SDK LangChain.js 流式输出 + 结构化生成
工作流编排 LangGraph AutoGen / CrewAI 有状态多步骤编排
持久化执行 Inngest Temporal 长时间运行 + 故障恢复
可观测性 OpenTelemetry LangSmith 执行链路追踪
模型路由 LiteLLM Proxy 自建路由层 多模型切换 + 负载均衡

构建一个好的规划引擎,本质上是在自主性可控性之间找到平衡。过度自主会导致不可预测的行为,过度控制则失去了 Agent 的价值。从本文的代码模板出发,根据你的具体场景逐步迭代,才是最务实的路径。记住:好的 Agent 不是最聪明的,而是最可靠的。

📚 相关文章