Agent Harness 的标准化之路

关键词

Agent Harness、多智能体协作、大语言模型应用标准化、LLM Agent 生命周期管理、推理调度协议、测试评估框架


摘要

从 2022 年底 ChatGPT 引爆大语言模型(LLM)以来,单智能体应用(如自动化编程助手 Cursor、论文阅读 ChatDOC)快速迭代,但真正能解决复杂跨域问题的多智能体协作(如 LangChain 的 AutoGPT 多分支、微软的 Semantic Kernel 的插件编排)仍处于“野蛮生长”阶段:智能体接口混乱、生命周期不一致、测试评估无统一标准、资源占用失控等问题,严重制约了 LLM Agent 从原型到生产落地的规模化。本文将从 Agent Harness 的问题背景与痛点切入,用“汽车生产线的工装夹具”这一生活化比喻,解析 Agent Harness 的核心概念、概念间的关系(含对比表格、ER 实体关系图、交互关系图),深入探讨其底层技术原理(如插件适配的抽象工厂模式、推理调度的马尔可夫决策过程模型),并结合基于 Python + LangGraph 构建的 AgentFlow Harness 项目,从环境安装、架构设计、接口实现、最佳实践等方面,展示标准化 Agent Harness 的落地路径。最后,还将梳理 Agent Harness 的发展历史、预测未来趋势,并给出实用的思考问题与参考资源。


1. 背景介绍

1.1 主题背景与重要性

1.1.1 从单智能体“试玩”到多智能体“生产”的迫切需求

时间回到 2023 年初:AutoGPT 作为初代自主推理 Agent 的代表,上线 3 天就吸引了 10 万+ GitHub 星标,它的核心逻辑是“Goal → Thought → Action → Observation → Loop”的 ReAct 推理链,看似能“自动完成目标”,但实际使用中却问题百出:比如找不到文件、无限循环、调用插件时错误百出、完成的任务完全偏离预期。这些问题,本质上不是 LLM 本身的能力不足(2024 年 GPT-4o、Claude 3.5 Sonnet 的推理能力已经远超初代 AutoGPT 的模型),而是缺乏一套“统一的连接、调度、监控、测试、部署的工具链与规范”——就像 100 年前福特汽车 T 型车诞生之前,汽车都是由工匠手工打造的,零件不通用、生产效率低、质量不稳定,直到工装夹具(Harness) 这种标准化的“连接与固定工具”出现,配合流水线生产模式,才让汽车实现了规模化生产与普及。

同样的逻辑,LLM Agent 想要从“个人试玩的玩具”变成“企业级生产的工具”,也需要一套标准化的“工装夹具”——这就是我们今天要讨论的 Agent Harness

1.1.2 Agent Harness 对 LLM 生态的价值

Agent Harness 的标准化,至少能带来以下 5 个方面的核心价值:

  1. 降低开发门槛:开发者不需要从零开始写插件适配、推理调度、监控告警等底层逻辑,只需要遵循 Harness 的规范,就能快速组装出符合需求的单/多智能体应用。
  2. 提高可复用性:插件、工具、推理模板、评估指标等都可以像积木一样,在不同的 Agent 项目中复用。
  3. 保证质量稳定性:通过统一的测试评估框架,可以对 Agent 的推理准确性、响应速度、资源占用等指标进行量化评估,及时发现并修复问题。
  4. 降低运维成本:通过统一的生命周期管理与监控调度系统,可以实现 Agent 的自动部署、弹性伸缩、故障恢复等功能。
  5. 促进生态繁荣:有了统一的规范,不同的 LLM 提供商(OpenAI、Anthropic、Meta)、插件提供商(SerpAPI、Wolfram Alpha、GitHub)、Agent 开发框架(LangChain、Semantic Kernel、CrewAI)就可以互联互通,形成一个开放、兼容的生态系统。

1.2 目标读者

本文的目标读者主要分为三类:

  1. LLM Agent 入门开发者:希望从零开始了解 Agent Harness 的核心概念与落地路径,快速上手构建标准化的 Agent 应用。
  2. 企业级 LLM 应用架构师/技术负责人:希望解决现有 Agent 项目的接口混乱、质量不稳定、运维成本高等问题,推动 Agent 应用在企业内的规模化落地。
  3. LLM 生态研究者/标准化爱好者:希望了解 Agent Harness 的发展历史、技术原理、未来趋势,参与或推动 Agent Harness 的标准化进程。

1.3 核心问题或挑战

目前,LLM Agent 从原型到生产落地,主要面临以下 5 个核心问题(也是 Agent Harness 标准化需要解决的核心挑战):

1.3.1 接口混乱:缺乏统一的插件、工具、LLM 提供商的适配接口

不同的 Agent 开发框架(比如 LangChain 用 Tool 类,Semantic Kernel 用 KernelFunction,CrewAI 用 AgentTools)有不同的插件/工具定义接口;不同的 LLM 提供商(比如 OpenAI 用 ChatCompletion,Anthropic 用 Messages API,Meta 用 Llama.cpp 的 completion 函数)有不同的 API 调用接口;甚至同一个 LLM 提供商的不同 API 版本,接口也会有细微的差异。这就导致开发者如果想要切换 Agent 框架、LLM 提供商或 API 版本,几乎要重写整个底层适配代码——就像你买了一辆福特汽车的轮胎,却装不上大众汽车的轮毂,因为螺丝的规格完全不一样。

1.3.2 生命周期不一致:缺乏统一的 Agent 启动、暂停、恢复、停止、部署的生命周期管理规范

目前,大多数 Agent 应用都是“一次性运行”的:启动后要么完成任务自动停止,要么出现问题直接崩溃,几乎没有暂停、恢复、重新初始化的功能;部署方式也五花八门:有的是用 Flask/FastAPI 写一个简单的 API 服务,有的是用 Docker 容器化部署,有的是用 Kubernetes 集群部署,但缺乏统一的部署规范与监控告警接口。这就导致 Agent 应用很难在生产环境中稳定运行——就像你买了一辆汽车,却没有方向盘、刹车、油门的统一操作规范,也没有维修店能帮你保养或维修。

1.3.3 推理调度无序:缺乏统一的多智能体协作推理调度协议

单智能体应用的推理调度相对简单,主要是 ReAct 或 Chain-of-Thought(CoT)的循环;但多智能体协作的推理调度就复杂得多:比如多个智能体是并行工作还是串行工作?哪个智能体先执行?如果某个智能体执行失败了怎么办?如何协调多个智能体的输出?目前,大多数多智能体协作框架(比如 LangChain 的 AgentExecutorMultiAgentRouter,CrewAI 的 CrewProcess)都有自己的推理调度逻辑,但缺乏统一的协议——就像你指挥一群工人盖房子,但没有统一的施工图纸、进度表、沟通方式,每个工人都按照自己的想法干活,最后盖出来的房子肯定是歪歪扭扭的。

1.3.4 测试评估无标准:缺乏统一的 Agent 测试用例、评估指标、评估方法

目前,大多数 Agent 应用的测试都是“人工测试”:开发者自己给 Agent 几个任务,看一下输出结果是否符合预期,完全没有量化的评估指标;即使有少数框架(比如 LangChain 的 LangSmith,Hugging Face 的 AgentBench)提供了测试评估功能,但评估指标、评估方法、测试用例库也不统一——就像你买了一辆汽车,却没有统一的汽车安全测试标准(比如 NCAP、IIHS),只能自己开着试一下,根本不知道这辆车的安全性到底怎么样。

1.3.5 资源占用失控:缺乏统一的 Agent 资源限制、监控告警、弹性伸缩规范

LLM 本身的资源占用就非常高(比如 GPT-4o 的 API 调用价格是每百万输入 tokens 5 美元,每百万输出 tokens 15 美元;本地部署的 Llama 3.1 405B 模型需要至少 800GB 的 GPU 显存),再加上插件调用、推理调度等额外的资源占用,如果没有统一的资源限制、监控告警、弹性伸缩规范,很容易导致资源浪费或系统崩溃——就像你给一辆汽车加了无限量的汽油,却没有限速器、油表、发动机温度报警器,最后要么汽油浪费了,要么发动机烧了。


2. 核心概念解析

2.1 生活化比喻:Agent Harness = 汽车生产线的“标准化工装夹具 + 自动化调度系统 + 质量检测站 + 维修保养车间”

为了让大家更容易理解 Agent Harness 的核心概念,我们可以把 LLM Agent 应用开发与生产 类比为 汽车的设计、生产、检测、维修、销售 整个生命周期:

  1. LLM = 汽车的“发动机”:提供核心动力(推理能力)。
  2. Agent 开发框架(比如 LangChain、Semantic Kernel)= 汽车的“底盘”:提供基本的结构(连接发动机、轮胎、方向盘等的基础框架)。
  3. 插件/工具(比如 SerpAPI、Wolfram Alpha)= 汽车的“附件”(比如导航仪、空调、雨刮器):扩展核心功能。
  4. Agent 实例(比如完成“预订明天从北京到上海的机票 + 预订明天晚上的酒店 + 查询明天上海的天气”的 Agent)= 一辆“完整的汽车”:由发动机、底盘、附件等组成,能够完成特定的任务。
  5. Agent Harness = 汽车生产线的“标准化工装夹具 + 自动化调度系统 + 质量检测站 + 维修保养车间”:
    • 标准化工装夹具:统一发动机、底盘、附件的连接接口与安装规范,确保零件通用、生产效率高、质量稳定。
    • 自动化调度系统:统一汽车的生产流程(比如先装发动机,再装轮胎,再装附件)、多个车间的协作方式(比如冲压车间生产零件后,自动送到焊接车间),确保生产有序、进度可控。
    • 质量检测站:统一汽车的安全测试、性能测试、舒适度测试标准,确保每一辆出厂的汽车都符合要求。
    • 维修保养车间:统一汽车的维修保养规范、故障诊断方法、备件更换流程,确保汽车在使用过程中稳定运行。

通过这个类比,我们可以很清楚地看到 Agent Harness 在 LLM Agent 生态中的核心地位:它不是“发动机”(LLM),也不是“底盘”(Agent 开发框架),而是连接“发动机”、“底盘”、“附件”的“标准化工具链与规范”,是 LLM Agent 从原型到生产落地的“基础设施”。

2.2 核心概念的明确定义

在给出核心概念的关系图之前,我们先对 Agent Harness 涉及的核心概念进行明确定义:

2.2.1 Agent Harness(智能体工装夹具/标准化工具链)

Agent Harness 是一套连接、调度、监控、测试、部署 LLM Agent 应用的标准化工具链与规范,它的核心目标是降低 Agent 应用的开发门槛、提高可复用性、保证质量稳定性、降低运维成本、促进生态繁荣。

2.2.2 Harness 规范(Harness Specification)

Harness 规范是 Agent Harness 的核心,它定义了 Agent Harness 各个组件的接口、行为、数据格式等标准,是实现不同组件互联互通的基础。目前,行业内已经有一些初步的 Harness 规范草案,比如:

  • OpenAI 的 Assistants API Specification:定义了单智能体的接口、行为、数据格式等标准。
  • LangChain 的 LangChain Hub Specification:定义了推理模板、提示词的接口、数据格式等标准。
  • Hugging Face 的 AgentBench Specification:定义了 Agent 测试评估的接口、数据格式、评估指标等标准。
  • 中国信通院的 大模型应用(Agent)技术规范:定义了 Agent 的分类、功能要求、性能要求、安全要求等标准。

但这些规范都是“碎片化”的,没有形成一套统一的、覆盖 Agent 整个生命周期的 Harness 规范——这也是我们今天讨论的“标准化之路”的核心内容之一。

2.2.3 Harness 组件(Harness Component)

Harness 组件是 Agent Harness 的“积木”,它遵循 Harness 规范,实现了 Agent 生命周期中的某个特定功能。常见的 Harness 组件包括:

  1. 模型适配层(Model Adaption Layer):统一不同 LLM 提供商、不同 API 版本的调用接口,实现模型的无缝切换。
  2. 插件/工具适配层(Tool/Plugin Adaption Layer):统一不同 Agent 框架、不同插件/工具提供商的定义接口,实现插件/工具的无缝切换与复用。
  3. 推理调度引擎(Reasoning Scheduling Engine):统一单/多智能体的推理调度逻辑,实现推理的有序、高效、容错。
  4. 生命周期管理器(Lifecycle Manager):统一 Agent 的启动、暂停、恢复、停止、部署的生命周期管理逻辑,实现 Agent 的稳定运行。
  5. 监控告警系统(Monitoring & Alerting System):统一 Agent 的资源占用、推理进度、错误日志等监控指标,实现问题的及时发现与告警。
  6. 测试评估框架(Testing & Evaluation Framework):统一 Agent 的测试用例、评估指标、评估方法,实现 Agent 的量化评估。
  7. 部署管理平台(Deployment Management Platform):统一 Agent 的容器化、Kubernetes 集群化部署逻辑,实现 Agent 的弹性伸缩与高可用。
2.2.4 Agent 生命周期(Agent Lifecycle)

Agent 生命周期是指 Agent 从“创建”到“销毁”的整个过程,它遵循 Harness 规范的生命周期管理标准。常见的 Agent 生命周期包括以下 7 个阶段:

  1. 初始化阶段(Initialization):加载 LLM、插件/工具、推理模板、配置文件等,初始化 Agent 的状态。
  2. 启动阶段(Startup):启动 Agent 的推理调度引擎,开始执行任务。
  3. 执行阶段(Execution):Agent 按照推理调度逻辑,调用 LLM、插件/工具,完成任务。
  4. 暂停阶段(Paused):暂停 Agent 的执行,保存当前的状态。
  5. 恢复阶段(Resumed):从暂停阶段保存的状态中恢复 Agent 的执行。
  6. 停止阶段(Stopped):停止 Agent 的执行,释放资源,但保留状态(可选)。
  7. 销毁阶段(Destroyed):彻底销毁 Agent,释放所有资源,清除所有状态。
2.2.5 推理模式(Reasoning Mode)

推理模式是指 Agent 调用 LLM、插件/工具完成任务的逻辑,它遵循 Harness 规范的推理调度标准。常见的推理模式包括:

  1. 单智能体串行推理(Single-Agent Serial Reasoning):只有一个智能体,按照 ReAct 或 CoT 的逻辑串行执行任务。
  2. 单智能体并行推理(Single-Agent Parallel Reasoning):只有一个智能体,但可以同时调用多个插件/工具(比如同时查询天气、查询机票、查询酒店),提高任务执行效率。
  3. 多智能体串行协作(Multi-Agent Serial Collaboration):有多个智能体,按照“前一个智能体的输出作为后一个智能体的输入”的逻辑串行协作完成任务(比如“需求分析师 Agent”分析用户需求,“架构师 Agent”根据需求设计架构,“开发者 Agent”根据架构写代码)。
  4. 多智能体并行协作(Multi-Agent Parallel Collaboration):有多个智能体,同时执行不同的子任务,最后合并所有子任务的输出完成总任务(比如“机票预订 Agent”、“酒店预订 Agent”、“天气查询 Agent”同时执行,最后合并结果给用户)。
  5. 多智能体混合协作(Multi-Agent Hybrid Collaboration):有多个智能体,既串行又并行地协作完成任务(比如“需求分析师 Agent”先分析需求,然后“架构师 Agent”、“数据库设计师 Agent”、“UI 设计师 Agent”同时执行,最后“集成工程师 Agent”合并所有结果)。
  6. 多智能体协商协作(Multi-Agent Negotiation Collaboration):有多个智能体,通过协商的方式解决冲突,共同完成任务(比如“价格谈判 Agent A”代表买方,“价格谈判 Agent B”代表卖方,通过多次协商达成一致的价格)。

2.3 概念间的关系

为了更清晰地展示 Agent Harness 涉及的核心概念之间的关系,我们将从以下 3 个方面进行分析:

2.3.1 概念核心属性维度对比(Markdown 表格)

首先,我们对 Agent Harness、Agent 开发框架、LLM、插件/工具 这 4 个最核心的概念,从“核心目标、核心功能、是否依赖其他组件、标准化程度、应用场景”这 5 个维度进行对比:

概念名称 核心目标 核心功能 是否依赖其他组件 标准化程度 应用场景
Agent Harness 连接、调度、监控、测试、部署 Agent 应用,实现规模化生产与落地 模型适配、插件/工具适配、推理调度、生命周期管理、监控告警、测试评估、部署管理 依赖 Agent 开发框架、LLM、插件/工具 低(目前只有碎片化的规范草案) 企业级 Agent 应用的开发、测试、部署、运维;Agent 生态的标准化建设
Agent 开发框架 提供连接 LLM、插件/工具的基础结构,降低 Agent 应用的开发门槛 提示词模板、记忆管理、推理链/图构建、插件/工具封装 依赖 LLM、插件/工具,可选依赖 Agent Harness 中(有一些通用的接口定义,但各框架差异较大) 单/多智能体应用的原型开发;小规模 Agent 应用的部署
LLM 提供核心推理能力,理解自然语言、生成自然语言、完成复杂任务 文本生成、代码生成、推理、翻译、摘要等 不依赖其他组件(可独立使用) 中(各 LLM 提供商的 API 差异较大,但有一些通用的接口封装) 各种需要自然语言处理或推理能力的应用;Agent 应用的核心动力
插件/工具 扩展 LLM 的核心能力,让 LLM 能够访问外部数据、执行外部操作 网络搜索、文件操作、API 调用、代码执行等 依赖 Agent 开发框架或 Agent Harness 低(各插件/工具提供商的 API 差异较大,各框架的封装方式也不同) 扩展 Agent 应用的功能;让 Agent 应用能够完成更复杂的跨域任务
2.3.2 概念联系的 ER 实体关系图(Mermaid 架构图)

接下来,我们用 Mermaid 的 ER 实体关系图,展示 Agent Harness、Harness 规范、Harness 组件、Agent 生命周期、推理模式、Agent 开发框架、LLM、插件/工具、Agent 实例 这 9 个核心概念之间的实体关系:

包含(由多个组件组成)

遵循(由多个规范组成)

遵循(每个组件遵循一个或多个规范)

遵循(每个生命周期阶段遵循一个或多个规范)

遵循(每个推理模式遵循一个或多个规范)

管理(管理多个智能体实例)

构建(构建多个智能体实例)

提供动力(为多个智能体实例提供推理能力)

扩展功能(为多个智能体实例提供扩展功能)

使用(每个智能体实例使用一个推理模式)

经历(每个智能体实例经历多个生命周期阶段)

AGENT_HARNESS

string

harness_id

PK

工装夹具唯一标识

string

harness_name

工装夹具名称

string

harness_version

工装夹具版本

string

description

工装夹具描述

HARNESS_SPEC

string

spec_id

PK

规范唯一标识

string

spec_name

规范名称

string

spec_version

规范版本

string

spec_type

规范类型(模型适配/插件适配/推理调度/生命周期管理/监控告警/测试评估/部署管理)

string

description

规范描述

HARNESS_COMPONENT

string

component_id

PK

组件唯一标识

string

component_name

组件名称

string

component_type

组件类型(模型适配层/插件/工具适配层/推理调度引擎/生命周期管理器/监控告警系统/测试评估框架/部署管理平台)

string

component_version

组件版本

string

spec_id

FK

遵循的规范唯一标识

string

description

组件描述

AGENT_LIFECYCLE

string

lifecycle_id

PK

生命周期唯一标识

string

lifecycle_name

生命周期名称

string

lifecycle_type

生命周期类型(初始化/启动/执行/暂停/恢复/停止/销毁)

string

spec_id

FK

遵循的规范唯一标识

string

description

生命周期描述

REASONING_MODE

string

mode_id

PK

推理模式唯一标识

string

mode_name

推理模式名称

string

mode_type

推理模式类型(单智能体串行/单智能体并行/多智能体串行/多智能体并行/多智能体混合/多智能体协商)

string

spec_id

FK

遵循的规范唯一标识

string

description

推理模式描述

AGENT_FRAMEWORK

string

framework_id

PK

框架唯一标识

string

framework_name

框架名称

string

framework_version

框架版本

string

description

框架描述

LLM

string

llm_id

PK

大模型唯一标识

string

llm_name

大模型名称

string

llm_provider

大模型提供商(OpenAI/Anthropic/Meta/百度/阿里/腾讯)

string

llm_version

大模型版本

string

description

大模型描述

TOOL_PLUGIN

string

tool_id

PK

插件/工具唯一标识

string

tool_name

插件/工具名称

string

tool_provider

插件/工具提供商(SerpAPI/Wolfram Alpha/GitHub/OpenAI)

string

tool_type

插件/工具类型(网络搜索/文件操作/API 调用/代码执行)

string

description

插件/工具描述

AGENT_INSTANCE

string

agent_id

PK

智能体实例唯一标识

string

agent_name

智能体实例名称

string

harness_id

FK

使用的工装夹具唯一标识

string

framework_id

FK

使用的开发框架唯一标识

string

llm_id

FK

使用的大模型唯一标识

string

mode_id

FK

使用的推理模式唯一标识

string

current_lifecycle_id

FK

当前生命周期阶段唯一标识

json

state

智能体实例当前状态

string

description

智能体实例描述

2.3.3 概念交互关系图(Mermaid 架构图)

最后,我们用 Mermaid 的架构图,展示 Agent Harness 各个组件与 Agent 实例、用户之间的交互关系

发送任务请求

转发任务请求

查询可用的智能体实例

创建/分配智能体实例

调用大模型

调用 OpenAI GPT-4o

调用 Anthropic Claude 3.5

调用 Meta Llama 3.1

调用插件/工具

调用 SerpAPI

调用 Wolfram Alpha

调用 GitHub API

保存当前状态

读取/更新状态

读取/更新状态

上报监控数据

上报监控数据

上报监控数据

存储监控数据

提供监控数据

展示监控数据

发送告警通知

调用智能体实例进行测试

读取测试结果

展示测试报告

构建 Docker 镜像

提供 Docker 镜像

部署到 Kubernetes 集群

管理智能体实例的容器

返回任务结果

用户

AgentFlow Harness
标准化工具链与规范

模型适配层
统一 LLM 调用接口

插件/工具适配层
统一插件/工具定义接口

推理调度引擎
统一推理调度逻辑

生命周期管理器
统一生命周期管理逻辑

监控告警系统
统一监控指标与告警逻辑

测试评估框架
统一测试用例与评估指标

部署管理平台
统一容器化与集群化部署逻辑

智能体实例池
多个标准化的智能体实例

OpenAI GPT-4o
大模型

Anthropic Claude 3.5 Sonnet
大模型

Meta Llama 3.1 405B
本地大模型

SerpAPI
网络搜索工具

Wolfram Alpha
科学计算工具

GitHub API
代码管理工具

PostgreSQL
状态存储数据库

Prometheus
监控数据存储

Grafana
监控可视化

Docker Hub
镜像仓库

Kubernetes
容器编排平台


3. 技术原理与实现

3.1 模型适配层的技术原理:抽象工厂模式

3.1.1 问题描述

如第 1.3.1 节所述,不同的 LLM 提供商、不同的 API 版本有不同的调用接口:

  • OpenAI 的 v1/chat/completions API 要求的请求体格式是:
    {
      "model": "gpt-4o",
      "messages": [
        {"role": "system", "content": "You are a helpful assistant."},
        {"role": "user", "content": "Hello!"}
      ],
      "temperature": 0.7
    }
    
  • Anthropic 的 v1/messages API 要求的请求体格式是:
    {
      "model": "claude-3-5-sonnet-20240620",
      "max_tokens": 1024,
      "messages": [
        {"role": "user", "content": "Hello!"}
      ],
      "system": "You are a helpful assistant.",
      "temperature": 0.7
    }
    
  • Meta Llama.cpp 的 completion 函数要求的参数是:
    from llama_cpp import Llama
    llm = Llama(model_path="./llama-3.1-8b-instruct.gguf")
    output = llm(
        prompt="You are a helpful assistant. Hello!",
        max_tokens=1024,
        temperature=0.7
    )
    

如果我们在 Agent 应用中直接调用这些不同的接口,那么当我们想要切换 LLM 提供商或 API 版本时,几乎要重写整个底层适配代码——这显然不符合“可复用性”和“可维护性”的要求。

3.1.2 解决方案:抽象工厂模式

抽象工厂模式(Abstract Factory Pattern)是一种创建型设计模式,它提供了一个创建一系列相关或相互依赖对象的接口,而无需指定它们具体的类。

我们可以用抽象工厂模式来设计模型适配层:

  1. 定义抽象产品接口:定义一个统一的 LLM 抽象类(或接口),包含所有 LLM 都应该有的方法(比如 chat_completiontext_completionembedding 等)。
  2. 定义具体产品类:为每个 LLM 提供商、每个 API 版本定义一个具体的 LLM 子类(比如 OpenAIGPT4oLLMAnthropicClaude35LLMLlamaCppLlama31LLM),实现 LLM 抽象类的所有方法。
  3. 定义抽象工厂接口:定义一个统一的 LLMFactory 抽象类(或接口),包含创建所有抽象产品的方法(比如 create_chat_llmcreate_text_llmcreate_embedding_llm 等)。
  4. 定义具体工厂类:为每个 LLM 提供商定义一个具体的 LLMFactory 子类(比如 OpenAILLMFactoryAnthropicLLMFactoryLlamaCppLLMFactory),实现 LLMFactory 抽象类的所有方法。

通过抽象工厂模式,我们可以在 Agent 应用中只依赖抽象产品接口和抽象工厂接口,而不依赖具体产品类和具体工厂类——当我们想要切换 LLM 提供商或 API 版本时,只需要切换具体工厂类即可,无需修改其他代码。

3.1.3 算法流程图(Mermaid 流程图)

接下来,我们用 Mermaid 的流程图,展示模型适配层的工作流程:

开始

读取 LLM 配置文件
(提供商、模型名称、API Key、参数等)

根据提供商创建具体 LLM 工厂
(OpenAILLMFactory/AnthropicLLMFactory/LlamaCppLLMFactory)

根据模型名称创建具体 LLM 产品
(OpenAIGPT4oLLM/AnthropicClaude35LLM/LlamaCppLlama31LLM)

验证具体 LLM 产品的可用性
(调用 ping 接口或发送测试请求)

验证是否成功?

返回具体 LLM 产品给 Agent 应用

处理验证失败的错误
(记录日志、发送告警、尝试切换到备用 LLM)

结束

3.1.4 数学模型:无(抽象工厂模式是一种设计模式,不需要数学模型)
3.1.5 算法源代码(Python 源代码)

接下来,我们用 Python 源代码实现模型适配层的抽象工厂模式:

from abc import ABC, abstractmethod
from typing import List, Dict, Any, Optional
import openai
import anthropic
from llama_cpp import Llama

# ------------------------------
# 1. 定义抽象产品接口:LLM
# ------------------------------
class LLM(ABC):
    """
    统一的 LLM 抽象类(接口),包含所有 LLM 都应该有的方法。
    """

    @abstractmethod
    def __init__(self, config: Dict[str, Any]):
        """
        初始化 LLM 产品。
        :param config: LLM 配置字典,包含提供商、模型名称、API Key、参数等。
        """
        pass

    @abstractmethod
    def chat_completion(
        self,
        messages: List[Dict[str, str]],
        temperature: float = 0.7,
        max_tokens: Optional[int] = None,
        **kwargs: Any
    ) -> str:
        """
        调用 LLM 的聊天补全接口。
        :param messages: 聊天消息列表,每个消息包含 role(system/user/assistant)和 content。
        :param temperature: 温度参数,控制输出的随机性(0-1 之间)。
        :param max_tokens: 最大输出 tokens 数。
        :param kwargs: 其他可选参数。
        :return: LLM 的输出文本。
        """
        pass

    @abstractmethod
    def embedding(
        self,
        text: str,
        **kwargs: Any
    ) -> List[float]:
        """
        调用 LLM 的文本嵌入接口。
        :param text: 需要嵌入的文本。
        :param kwargs: 其他可选参数。
        :return: 文本的嵌入向量(浮点数列表)。
        """
        pass

    @abstractmethod
    def ping(self) -> bool:
        """
        验证 LLM 产品的可用性(调用 ping 接口或发送测试请求)。
        :return: 可用性结果(True/False)。
        """
        pass

# ------------------------------
# 2. 定义具体产品类:OpenAI LLM
# ------------------------------
class OpenAILLM(LLM):
    """
    OpenAI LLM 的具体产品类,实现 LLM 抽象类的所有方法。
    """

    def __init__(self, config: Dict[str, Any]):
        """
        初始化 OpenAI LLM 产品。
        :param config: OpenAI LLM 配置字典,必须包含:
            - api_key: OpenAI API Key
            - model_name: OpenAI 模型名称(比如 gpt-4o, gpt-3.5-turbo)
        可选包含:
            - api_base: OpenAI API Base URL(用于代理或第三方 API)
            - organization: OpenAI 组织 ID
            - default_temperature: 默认温度参数
            - default_max_tokens: 默认最大输出 tokens 数
        """
        self.config = config
        self.api_key = config.get("api_key")
        self.model_name = config.get("model_name")
        self.api_base = config.get("api_base", "https://api.openai.com/v1")
        self.organization = config.get("organization")
        self.default_temperature = config.get("default_temperature", 0.7)
        self.default_max_tokens = config.get("default_max_tokens", 1024)

        # 初始化 OpenAI 客户端
        self.client = openai.OpenAI(
            api_key=self.api_key,
            base_url=self.api_base,
            organization=self.organization
        )

    def chat_completion(
        self,
        messages: List[Dict[str, str]],
        temperature: Optional[float] = None,
        max_tokens: Optional[int] = None,
        **kwargs: Any
    ) -> str:
        """
        调用 OpenAI 的聊天补全接口。
        """
        temperature = temperature or self.default_temperature
        max_tokens = max_tokens or self.default_max_tokens

        try:
            response = self.client.chat.completions.create(
                model=self.model_name,
                messages=messages,
                temperature=temperature,
                max_tokens=max_tokens,
                **kwargs
            )
            return response.choices[0].message.content.strip()
        except Exception as e:
            raise RuntimeError(f"OpenAI chat completion failed: {str(e)}") from e

    def embedding(
        self,
        text: str,
        **kwargs: Any
    ) -> List[float]:
        """
        调用 OpenAI 的文本嵌入接口。
        """
        try:
            # OpenAI 的嵌入模型默认是 text-embedding-3-small
            embedding_model = kwargs.get("embedding_model", "text-embedding-3-small")
            response = self.client.embeddings.create(
                model=embedding_model,
                input=text
            )
            return response.data[0].embedding
        except Exception as e:
            raise RuntimeError(f"OpenAI embedding failed: {str(e)}") from e

    def ping(self) -> bool:
        """
        验证 OpenAI LLM 产品的可用性(发送测试聊天请求)。
        """
        try:
            self.chat_completion(
                messages=[{"role": "user", "content": "ping"}],
                max_tokens=5
            )
            return True
        except Exception:
            return False

# ------------------------------
# 3. 定义具体产品类:Anthropic LLM
# ------------------------------
class AnthropicLLM(LLM):
    """
    Anthropic LLM 的具体产品类,实现 LLM 抽象类的所有方法。
    """

    def __init__(self, config: Dict[str, Any]):
        """
        初始化 Anthropic LLM 产品。
        :param config: Anthropic LLM 配置字典,必须包含:
            - api_key: Anthropic API Key
            - model_name: Anthropic 模型名称(比如 claude-3-5-sonnet-20240620, claude-3-opus-20240229)
        可选包含:
            - api_base: Anthropic API Base URL(用于代理或第三方 API)
            - default_temperature: 默认温度参数
            - default_max_tokens: 默认最大输出 tokens 数
        """
        self.config = config
        self.api_key = config.get("api_key")
        self.model_name = config.get("model_name")
        self.api_base = config.get("api_base", "https://api.anthropic.com/v1")
        self.default_temperature = config.get("default_temperature", 0.7)
        self.default_max_tokens = config.get("default_max_tokens", 1024)

        # 初始化 Anthropic 客户端
        self.client = anthropic.Anthropic(
            api_key=self.api_key,
            base_url=self.api_base
        )

    def chat_completion(
        self,
        messages: List[Dict[str, str]],
        temperature: Optional[float] = None,
        max_tokens: Optional[int] = None,
        **kwargs: Any
    ) -> str:
        """
        调用 Anthropic 的聊天补全接口。
        注意:Anthropic 的 API 要求 system 消息作为单独的参数,而不是放在 messages 列表中。
        """
        temperature = temperature or self.default_temperature
        max_tokens = max_tokens or self.default_max_tokens

        # 分离 system 消息和其他消息
        system_message = ""
        filtered_messages = []
        for message in messages:
            if message["role"] == "system":
                system_message += message["content"] + "\n"
            else:
                filtered_messages.append(message)

        try:
            response = self.client.messages.create(
                model=self.model_name,
                max_tokens=max_tokens,
                messages=filtered_messages,
                system=system_message.strip() if system_message else None,
                temperature=temperature,
                **kwargs
            )
            return response.content[0].text.strip()
        except Exception as e:
            raise RuntimeError(f"Anthropic chat completion failed: {str(e)}") from e

    def embedding(
        self,
        text: str,
        **kwargs: Any
    ) -> List[float]:
        """
        调用 Anthropic 的文本嵌入接口。
        注意:Anthropic 目前(20249 月)还没有官方的文本嵌入 API,这里我们抛出一个 NotImplementedError。
        如果你需要使用 Anthropic 的文本嵌入功能,可以使用第三方 API 或者其他 LLM 提供商的嵌入 API。
Logo

中国智能体开发者社区,聚焦智能体与大模型开发,提供前沿资讯、实用工具链、开源项目及行业案例。通过技术沙龙、开发者大赛等活动,促进经验交流与协作,助力开发者快速构建创新智能应用。

更多推荐