从零开发AI Agent:Python实现大模型调用、工具调用与任务自动执行
引言:AI Agent的兴起与开发痛点
AI Agent(智能代理)是当前人工智能领域最前沿的技术之一。

它不再是简单的问答工具,而是具备感知环境、制定计划、调用工具并自主执行复杂任务的自主智能系统。从ChatGPT横空出世,到Claude、Gemini等大语言模型(LLM)相继发布,AI Agent彻底改变了开发者构建自动化系统的思路。传统软件开发侧重于代码逻辑和算法实现,而AI Agent则需要深度桥接LLM的自然语言输出与外部世界的交互,这带来了前所未有的开发范式转变。
AI Agent的概念起源于ReAct框架(Reason + Act),最早在2022年由谷歌DeepMind团队提出,其核心思想是将大型语言模型的推理过程与实际行动相结合。ReAct框架将每个推理步骤拆分为“思考”(Reasoning)、“行动”(Acting)和“观察”(Observation)三个阶段,这种设计显著提升了模型在复杂任务上的表现能力。2023年OpenAI正式推出工具调用API后,AI Agent正式进入大规模应用阶段。开发者不再局限于单轮对话,而是可以构建支持实时数据访问、API集成和多步骤执行的自主系统。
然而,开发AI Agent绝非易事。核心痛点体现在以下几个方面:
- API集成与认证:如何安全调用OpenAI、Anthropic或Google等主流API?需要处理密钥管理、速率限制(RPM/TMP)、错误重试和流式输出等技术细节。特别是在生产环境中,频繁的API调用可能触发速率限制或导致成本激增,因此需要合理的缓存策略和重试机制。
- 工具调用机制:LLM如何决定调用外部函数?模型输出必须兼容JSON格式的函数定义,才能正确解析参数并执行。模型的函数调用能力源于其对JSON Schema的理解能力,以及在生成过程中对工具描述的上下文关联判断。
- 任务自动执行闭环:从用户输入到最终结果的完整流程,包括状态管理、对话历史记忆、多轮对话协调,以及工具执行后的反馈迭代。这种闭环设计要求Agent具备动态规划能力,能够根据工具返回的结果调整后续步骤。
- 健壮性与扩展性:LLM存在幻觉、token消耗过高、工具失败或API变更等问题,如何优雅处理?如何实现异步并行、缓存优化和日志追踪?特别是在多Agent协作场景中,如何协调不同Agent之间的通信和状态同步。
这些痛点直接影响开发效率和系统稳定性。本文将从零开始,使用纯Python技术栈,构建一个完整可用的AI Agent框架。我们将逐步实现大模型调用、工具调用和任务自动执行,并通过实战案例加深理解。最后讨论常见踩坑与优化策略,帮助读者快速上手,甚至扩展到生产级系统。
本文目标是提供可直接运行的代码示例,并深入讲解原理,避免空泛理论。所有代码基于Python 3.10+和openai库(v1.0+),可无缝迁移到Ollama等本地模型。相比其他语言,Python以其简洁的语法和丰富的生态系统,成为AI Agent开发的理想选择。开发者可以轻松集成各种工具库,例如用于调试的pdb模块,或用于性能分析的cProfile。此外,Python的跨平台特性使其Agent可以轻松部署在服务器、边缘设备甚至移动端。
为了更好地理解AI Agent的潜在应用场景,我们来看几个典型的用例。首先,在数据分析领域,Agent可以自动调用计算工具和API接口,完成复杂的统计分析任务。例如,金融分析师可以使用Agent分析股票数据、生成投资报告,并根据实时市场数据调整策略。其次,在自动化运维中,Agent可以感知系统状态,调用命令行工具或API执行部署、故障排查和性能优化。这种自主能力显著降低了人工干预需求,提升了系统可靠性。
然而,构建AI Agent也会遇到一系列挑战。例如,模型的“幻觉”问题可能导致生成看似合理但实际上错误的答案,尤其是在需要高精度数据的场景下。此外,工具调用过程可能存在无限循环风险,例如Agent反复尝试调用同一工具而无法获得有效结果。因此,合理的循环控制、错误恢复机制和上下文管理至关重要。
核心原理:大模型调用、工具调用与任务自动执行
大模型调用原理
大模型调用是AI Agent的基础。它通过HTTP接口与LLM进行交互,核心流程包括:
- 准备API密钥和模型参数。
- 构建消息历史(Message History):系统提示(System Prompt)、用户消息、助手消息。
- 发送请求并解析响应。
- 处理流式输出(stream)以实现实时交互。
主流LLM提供商采用聊天完成接口(Chat Completions)。OpenAI库是最简洁的Python SDK,支持异步调用和工具集成。使用方式包括:
- 直接POST请求到
https://api.openai.com/v1/chat/completions,使用application/json格式。 - 利用官方SDK简化认证和序列化。
代码示例1:基础大模型调用
import openai
import os
import json
from typing import List, Dict
# 推荐从.env文件或环境变量读取密钥
# os.environ["OPENAI_API_KEY"] = "sk-your-api-key-here"
def call_llm(prompt: str, model: str = "gpt-3.5-turbo", max_tokens: int = 500, temperature: float = 0.7) -> str:
"""基础大模型调用函数"""
# 系统提示优化上下文
messages: List[Dict[str, str]] = [
{"role": "system", "content": "你是一个有帮助、专业的助手,回答要简洁准确。"},
{"role": "user", "content": prompt}
]
try:
response = openai.ChatCompletion.create(
model=model,
messages=messages,
max_tokens=max_tokens,
temperature=temperature,
top_p=0.9,
frequency_penalty=0.0,
presence_penalty=0.0
)
# 提取文本内容
content = response.choices[0].message.content.strip()
return content
except Exception as e:
return f"调用失败:{str(e)} - 请检查API密钥和网络连接"
# 示例调用
if __name__ == "__main__":
test_prompt = "请用Python代码实现一个简单的斐波那契数列生成器,并解释其时间复杂度"
result = call_llm(test_prompt)
print("模型响应:")
print(result)
在这个示例中,call_llm函数封装了调用逻辑。messages列表保持上下文连贯,避免重复发送完整提示。参数如temperature控制生成随机性(0.0最确定,1.0最创造性),max_tokens防止无限输出。实际项目中,建议使用response对象的usage属性监控token消耗,并实现重试逻辑(使用tenacity库实现指数退避)。例如,在处理敏感数据时,可以设置max_tokens=200以减少成本,并结合top_p=0.95进行一定程度的随机性控制以获得更自然的回答。
此外,top_p参数(核采样)进一步控制生成分布,通过累积概率密度函数决定是否选择下一个token。实际应用中,这有助于避免过于保守或激进的输出。在生产环境中,合理的token管理至关重要,因为每个模型都有严格的上下文窗口限制(例如GPT-3.5-turbo的8K tokens)。如果对话历史过长,建议使用滑动窗口技术定期清理旧消息,或者采用摘要机制将历史浓缩成关键点。
大模型调用的本质是理解其输入输出格式:模型将用户消息转换为内部表示,通过注意力机制生成下一个token序列。正确构建系统提示是关键——它能显著提升回答质量和一致性。例如,一个精心设计的系统提示可以包含角色定义、行为准则和特定任务约束,从而引导模型生成符合预期的输出。研究表明,优化后的提示词工程(Prompt Engineering)可以使模型性能提升20-30%。在实际开发中,建议使用chain-of-thought(CoT)提示技巧,引导模型逐步推理,这对于复杂问题尤其有效。
工具调用机制详解
工具调用(Tool Use / Function Calling)是LLM的革命性能力。它允许模型在响应中声明需要调用外部工具,而非直接生成答案。原理基于:
- 函数定义JSON Schema:描述工具名称、描述和参数结构。JSON Schema是一种标准化的数据验证格式,用于定义API接口的输入参数类型、约束和描述信息。每个工具的函数定义必须严格遵循此格式,包括
type、properties、required等字段。 - 模型决策过程:在生成响应时,LLM会输出
tool_calls数组,指定调用哪个工具、参数是什么。模型在训练时学习了如何识别需要调用工具的场景,并通过微调生成符合JSON格式的tool_calls输出。 - 代理解析执行:后端接收
tool_calls,执行工具函数,获取结果,并将结果作为新消息追加到历史中。 - 迭代闭环:直到模型决定提供最终答案。
这种机制突破了LLM知识截止日期问题,支持实时数据访问(如API、数据库、计算器)。OpenAI API最早在2023年推出,之后被广泛采用。工具调用不仅限于单一工具,还支持并行调用多个工具和嵌套调用。
代码示例2:带工具调用的完整LLM调用
import openai
import json
from typing import List, Dict, Callable, Any
def calculator(a: float, b: float) -> float:
"""计算两个数的和"""
return a + b
def get_weather(city: str) -> str:
"""获取指定城市的天气(模拟真实API调用)"""
# 生产环境应替换为真实API如OpenWeatherMap
weather_data = {
"北京": "晴朗,18°C",
"上海": "多云,25°C",
"广州": "阵雨,30°C"
}
return weather_data.get(city, f"无法获取{city}天气信息")
def get_current_time() -> str:
"""获取当前时间"""
from datetime import datetime
return datetime.now().strftime("%Y-%m-%d %H:%M:%S")
tools = [
{
"type": "function",
"function": {
"name": "calculator",
"description": "执行基本数学计算",
"parameters": {
"type": "object",
"properties": {
"a": {"type": "number", "description": "第一个数字"},
"b": {"type": "number", "description": "第二个数字"}
},
"required": ["a", "b"]
}
}
},
{
"type": "function",
"function": {
"name": "get_weather",
"description": "获取指定城市的天气信息",
"parameters": {
"type": "object",
"properties": {
"city": {"type": "string", "description": "城市名称"}
},
"required": ["city"]
}
}
},
{
"type": "function",
"function": {
"name": "get_current_time",
"description": "获取当前系统时间",
"parameters": {
"type": "object",
"properties": {},
"required": []
}
}
}
]
def call_llm_with_tools(prompt: str, max_steps: int = 5) -> str:
"""带工具调用的高级调用函数"""
messages: List[Dict[str, Any]] = [{"role": "user", "content": prompt}]
tool_functions: Dict[str, Callable] = {
"calculator": calculator,
"get_weather": get_weather,
"get_current_time": get_current_time
}
steps = 0
final_response = None
while steps < max_steps and final_response is None:
response = openai.ChatCompletion.create(
model="gpt-3.5-turbo",
messages=messages,
tools=tools,
tool_choice="auto",
temperature=0.3,
max_tokens=800
)
assistant_message = response.choices[0].message
if assistant_message.content:
final_response = assistant_message.content
break
# 处理工具调用
if hasattr(assistant_message, 'tool_calls') and assistant_message.tool_calls:
tool_call = assistant_message.tool_calls[0]
func_name = tool_call.function.name
args_str = tool_call.function.arguments
try:
func = tool_functions.get(func_name)
if func:
args = json.loads(args_str) if args_str else {}
result = func(**args)
# 追加消息历史
messages.append({
"role": "assistant",
"content": assistant_message.content if assistant_message.content else "",
"tool_calls": [tool_call.to_dict()]
})
messages.append({
"role": "tool",
"tool_call_id": tool_call.id,
"content": str(result)
})
else:
messages.append({"role": "assistant", "content": f"未找到工具:{func_name}"})
except Exception as e:
messages.append({"role": "tool", "tool_call_id": tool_call.id, "content": f"执行错误:{str(e)}"})
steps += 1
else:
break
return final_response or "任务未能完成。"
# 测试调用
if __name__ == "__main__":
test_query = "上海今天的天气怎么样?现在几点了?1加2等于多少?"
result = call_llm_with_tools(test_query)
print("Agent最终响应:")
print(result)
上述代码的关键是正确解析tool_calls对象(.to_dict()用于序列化)和构建工具字典映射。tool_choice="auto"让模型自主决定是否调用工具。实际使用时,建议验证参数类型(使用jsonschema库)并处理并行工具调用(OpenAI支持一次多个tool_calls)。此机制本质上是LLM的"决策 + 执行"循环。
JSON Schema在工具调用中的重要性在于,它不仅定义了参数结构,还提供了人类可读的描述信息。模型通过理解这些描述来决定是否调用特定工具。例如,当用户询问天气时,模型会匹配get_weather工具的描述,并解析city参数。对于更复杂的场景,可以定义多个工具并通过tool_choice参数控制模型的行为。tool_choice选项包括auto(自动)、none(禁用工具调用)和具体工具名称(强制调用特定工具)。
此外,工具调用支持流式输出,这在实时交互场景中尤为重要。通过设置stream=True,可以实现边生成边输出响应,显著提升用户体验。在生产环境中,建议结合异步编程模型(如asyncio)处理高并发调用,以避免阻塞事件循环。
任务自动执行的核心原理
任务自动执行构建在工具调用之上,形成闭环Agent系统。典型架构基于ReAct框架(Reason + Act):
- 观察(Observation):接收用户输入或环境状态。通过消息历史管理,Agent可以感知到当前上下文和之前的工具执行结果。
- 思考(Reasoning):模型分析问题、规划步骤。模型在生成响应时,会根据系统提示和对话历史思考如何解决问题,可能决定调用工具或直接回答。
- 行动(Action):决定并调用工具。模型在生成阶段输出
tool_calls数组,指定需要执行的操作。 - 执行(Execution):运行工具函数并获取反馈。工具执行完成后,结果被追加到消息历史中,作为下一次调用的输入。
- 记忆(Memory):存储对话历史和工具结果,支持多轮对话。合理的记忆管理可以防止上下文溢出,并保持对话连贯性。
- 停止条件:达到最终答案、最大步数(避免无限循环)或用户确认。通过设置
max_steps参数和检查assistant_message.content字段,Agent可以判断何时停止并返回最终答案。
实现原理包括循环控制、状态机管理和反馈迭代。Agent循环运行直到满足停止条件。核心挑战是管理上下文窗口和工具副作用。以下是一个基于ReAct框架的详细工作流程图示:
用户输入
↓
系统提示 + 消息历史
↓
模型生成响应
├── 有内容 → 返回最终答案
└── 有tool_calls → 执行工具 + 更新消息历史
↓
循环至多max_steps步
↓
返回最终答案
这种循环设计使得Agent具备了自主完成多步骤任务的能力。例如,一个复杂的查询可能需要先获取天气数据,再进行计算,最后生成报告。每个步骤的执行都依赖于前一步的结果,从而形成完整的闭环。
在实际实现中,任务自动执行还涉及状态管理。例如,可以使用字典或数据库存储Agent的当前状态,包括已执行的工具、剩余步数和最终答案。这样的设计有助于在遇到错误时进行恢复,或者在多轮对话中保持上下文一致性。
实战案例:构建一个完整的AI Agent实现
下面我们通过实战构建一个端到端的AI Agent——“天气与计算专家”。它支持用户自然语言查询,并自动调用工具执行任务。
Agent类设计与实现
import openai
import json
import time
from typing import List, Dict, Callable, Any
from datetime import datetime
class AIAgent:
def __init__(self, model: str = "gpt-3.5-turbo"):
self.model = model
self.tools = []
self.tool_functions: Dict[str, Callable] = {}
self.memory: List[Dict[str, Any]] = []
self.max_steps = 5
self.retry_attempts = 3
def add_tool(self, name: str, description: str, params_schema: Dict, func: Callable):
"""注册工具"""
tool_def = {
"type": "function",
"function": {
"name": name,
"description": description,
"parameters": params_schema
}
}
self.tools.append(tool_def)
self.tool_functions[name] = func
def _format_tools(self) -> List[Dict]:
return self.tools
def _build_messages(self, user_input: str) -> List[Dict[str, Any]]:
"""构建消息历史,保留记忆"""
messages = self.memory + [{"role": "user", "content": user_input}]
return messages
def run(self, user_input: str) -> str:
"""执行Agent循环任务"""
messages = self._build_messages(user_input)
steps = 0
final_answer = None
last_error = None
while steps < self.max_steps and final_answer is None:
response = openai.ChatCompletion.create(
model=self.model,
messages=messages,
tools=self._format_tools(),
tool_choice="auto",
temperature=0.3,
max_tokens=800
)
assistant_message = response.choices[0].message
messages.append({"role": "assistant", "content": assistant_message.content or ""})
# 处理工具调用
if hasattr(assistant_message, 'tool_calls') and assistant_message.tool_calls:
tool_call = assistant_message.tool_calls[0]
func_name = tool_call.function.name
args_str = tool_call.function.arguments
try:
func = self.tool_functions.get(func_name)
if func:
args = json.loads(args_str) if args_str else {}
result = func(**args)
messages.append({
"role": "tool",
"tool_call_id": tool_call.id,
"content": str(result)
})
else:
messages.append({"role": "tool", "tool_call_id": tool_call.id, "content": "工具不存在"})
except Exception as e:
last_error = str(e)
messages.append({"role": "tool", "tool_call_id": tool_call.id, "content": f"执行错误:{last_error}"})
# 检查最终答案
if assistant_message.content and not hasattr(assistant_message, 'tool_calls'):
final_answer = assistant_message.content
break
steps += 1
time.sleep(0.5) # 避免速率限制
self.memory = messages[-10:] # 限制记忆长度
return final_answer or last_error or "任务执行失败,请检查工具或模型"
# 注册工具
def get_weather(city: str) -> str:
"""真实天气API调用(示例)"""
# 替换为实际API:requests.get("https://api.openweathermap.org/...", params=...)
return f"{city}的天气:晴朗,25°C,风速3m/s"
def calculator(a: float, b: float) -> float:
"""数学计算工具"""
return a + b
def get_time() -> str:
"""获取当前时间"""
return datetime.now().strftime("%Y-%m-%d %H:%M:%S")
# 实例化Agent
agent = AIAgent(model="gpt-3.5-turbo")
agent.add_tool("get_weather", "获取城市天气", {"type": "object", "properties": {"city": {"type": "string"}}}, get_weather)
agent.add_tool("calculator", "计算两个数字", {"type": "object", "properties": {"a": {"type": "number"}, "b": {"type": "number"}}}, calculator)
agent.add_tool("get_time", "获取当前时间", {"type": "object", "properties": {}}, get_time)
# 运行示例
if __name__ == "__main__":
user_query = "上海今天的天气如何?现在几点了?1加3等于多少?帮我计算一下"
result = agent.run(user_query)
print("AI Agent最终输出:")
print(result)
此Agent类包含内存管理(self.memory限制历史长度)、错误重试和步数控制。add_tool方法注册工具时同时保存映射。实战中,该Agent可处理复杂多步骤查询,并自动迭代。
在实战案例中,我们可以看到Agent类通过add_tool方法灵活注册自定义工具。这使得用户可以根据特定需求扩展Agent的功能。例如,可以添加一个数据库查询工具,用于检索历史数据,或者一个文件操作工具,用于读取配置文件。注册工具时,参数params_schema必须遵循JSON Schema格式,确保模型能够正确解析参数。
此外,Agent类的run方法实现了核心的循环逻辑。在每次迭代中,Agent会构建消息历史,调用LLM生成响应。如果响应包含tool_calls,则执行对应的工具函数并将结果追加到消息历史中。如果响应直接包含内容,则停止循环并返回答案。通过限制max_steps为5,我们可以有效防止无限循环,即使在工具调用失败的情况下,Agent也会在一定步数后停止并报告错误。
在这个示例中,我们还演示了如何添加多个工具并注册到Agent实例中。实际应用中,可以使用更复杂的工具,例如集成第三方API或执行Python函数。这些工具可以根据用户查询动态选择执行,从而实现更智能的自动化流程。
为了进一步丰富Agent的功能,可以扩展其支持多轮对话和记忆持久化。例如,在__init__方法中添加一个可选参数memory_file,并使用json库在每次运行后保存self.memory到文件中,下次初始化时从文件中加载。这样可以实现跨会话的记忆保留,提升Agent的连贯性。
运行输出示例(假设调用成功):
AI Agent最终输出:
上海今天的天气是晴朗,25°C,风速3m/s。现在时间是2024-10-01 12:34:56。1加3等于4。
工具调用实战扩展
为了演示工具调用的高级用法,我们可以添加一个支持并行调用的示例。以下是一个修改后的call_llm_with_tools函数,支持同时调用多个工具:
def call_llm_with_tools(prompt: str, max_steps: int = 5) -> str:
"""支持并行工具调用的高级调用函数"""
messages = [{"role": "user", "content": prompt}]
tool_functions = {
"calculator": calculator,
"get_weather": get_weather,
"get_current_time": get_current_time
}
steps = 0
final_response = None
while steps < max_steps and final_response is None:
response = openai.ChatCompletion.create(
model="gpt-3.5-turbo",
messages=messages,
tools=tools,
tool_choice="auto",
temperature=0.3,
max_tokens=800
)
assistant_message = response.choices[0].message
if assistant_message.content:
final_response = assistant_message.content
break
if hasattr(assistant_message, 'tool_calls') and assistant_message.tool_calls:
tool_calls = assistant_message.tool_calls
for tool_call in tool_calls:
func_name = tool_call.function.name
args_str = tool_call.function.arguments
try:
func = tool_functions.get(func_name)
if func:
args = json.loads(args_str) if args_str else {}
result = func(**args)
messages.append({
"role": "assistant",
"content": assistant_message.content if assistant_message.content else "",
"tool_calls": [tool_call.to_dict()]
})
messages.append({
"role": "tool",
"tool_call_id": tool_call.id,
"content": str(result)
})
except Exception as e:
messages.append({
"role": "tool",
"tool_call_id": tool_call.id,
"content": f"执行错误:{str(e)}"
})
steps += 1
else:
break
return final_response or "任务未能完成。"
此扩展支持并行处理多个tool_calls,提高了Agent处理复杂查询的效率。例如,用户可以同时询问天气和当前时间,Agent可以一次性调用两个工具并返回结果。
记忆管理与持久化
在Agent类中,self.memory属性用于存储对话历史。为了进一步提升其功能,我们可以实现一个save_memory方法,将内存持久化到文件:
def save_memory(self, file_path: str = "agent_memory.json"):
"""保存记忆到文件"""
with open(file_path, 'w') as f:
json.dump(self.memory, f, ensure_ascii=False, indent=2)
def load_memory(self, file_path: str = "agent_memory.json"):
"""从文件加载记忆"""
if os.path.exists(file_path):
with open(file_path, 'r') as f:
self.memory = json.load(f)
通过这样的扩展,Agent可以在重新启动后继续之前的对话,使其具备更强的长期记忆能力。这对于多轮对话场景尤其有用。
踩坑与优化建议
开发AI Agent时,常见问题包括:
- API限速与成本:OpenAI有每分钟速率限制。使用
backoff库实现重试,并监控response.usage中的token消耗。实际成本取决于token数量和调用频率。 - token窗口溢出:对话历史过长导致超限。采用滑动窗口或摘要机制压缩记忆。可以定期清理旧消息,或使用提示技巧引导模型生成摘要。
- 工具执行异常:工具函数可能抛出异常。必须使用
try-except捕获,并将错误反馈给模型。建议在工具函数中添加详细的错误处理逻辑。 - 模型幻觉:即使调用工具,模型有时仍会生成不一致答案。加入系统提示"如果不确定,请使用工具"。或者通过多次提示迭代进行验证。
- 参数解析错误:
tool_calls参数为JSON字符串。生产环境应使用jsonschema验证。可以使用jsonschema库在执行前验证参数。 - 并行工具调用:OpenAI支持一次多个工具。需修改代码以处理
tool_calls列表。注意处理每个tool_call时可能出现的异常。 - 异步优化:高并发场景下,使用
asyncio和aiohttp代替同步请求。异步编程可以显著提升Agent的响应速度。 - 调试困难:添加详细日志记录模型输入、工具调用轨迹和响应。使用
logging模块记录关键步骤,便于排查问题。
优化建议:
- 使用
python-dotenv管理密钥。可以通过load_dotenv()加载.env文件,避免硬编码密钥。 - 集成向量数据库(如Chroma)存储长期记忆。使用向量数据库可以实现更复杂的记忆搜索和总结。
- 添加进度条显示执行步骤。使用
tqdm库在循环中添加进度提示,增强用户体验。 - 单元测试工具函数和Agent循环。编写单元测试确保工具函数正确性,并测试Agent的循环逻辑。
- 迁移到本地模型(如Ollama + llama.cpp)降低成本和隐私风险。使用本地模型可以完全避免API费用,并保护数据隐私。
- 实现智能重试机制。使用
tenacity库根据错误类型和次数动态调整重试策略。 - 添加对话历史摘要功能。在每次迭代后,对消息历史进行总结,保持上下文窗口在可控范围内。
- 支持自定义系统提示。通过
__init__方法添加system_prompt参数,并将其添加到messages列表中。 - 监控Agent性能。通过记录每次调用的token消耗和步数,分析Agent在不同场景下的性能表现。
通过上述建议,您可以构建稳定高效的Agent系统。例如,在处理高频查询时,可以实现一个简单的缓存层,将近期结果存储在内存中,避免重复调用API。对于复杂任务,可以使用分层提示技巧,先让模型规划步骤,然后执行每个步骤。
常见问题FAQ
Q1: 如何处理API密钥泄露风险?
A: 使用环境变量或python-dotenv加载密钥,避免硬编码。定期轮换密钥,并使用密钥管理系统如HashiCorp Vault管理敏感信息。
Q2: Agent循环中如何避免无限循环?
A: 通过设置max_steps参数,并在每次迭代后检查assistant_message.content字段决定是否停止。还可以添加tool_call_count限制以防止重复调用同一工具。
Q3: 如何处理工具函数抛出异常?
A: 在工具函数中添加try-except块,将错误信息返回给模型。或者在Agent的run方法中捕获异常并提供友好错误提示。
Q4: 为什么模型有时不调用工具?
A: 可能因为系统提示不够明确,或者模型在某些场景下更倾向于直接回答。可以通过调整tool_choice参数为"none"强制模型调用工具,或者优化提示词引导模型决策。
Q5: 如何支持多轮对话?
A: 保留完整的消息历史,并在每次运行时传递给call_llm或run方法。可以通过self.memory属性管理对话上下文。
Q6: 如何优化Agent的响应速度?
A: 使用异步编程模型替代同步调用,减少等待时间。也可以通过缓存工具结果或使用更高效的模型(如GPT-4o-mini)提升速度。
总结与展望
本文从零介绍了AI Agent的Python实现,涵盖大模型调用、工具调用和任务自动执行的核心原理。我们构建了一个可直接运行的天气与计算Agent,展示了完整闭环。代码示例基于纯Python和OpenAI API,可轻松扩展。
通过本文,读者可以深入理解AI Agent的原理和实现细节,包括消息历史的构建、工具调用的JSON Schema解析、ReAct循环的各个阶段,以及内存管理的最佳实践。这些知识构成了构建生产级Agent的基础。
未来展望包括:
- 多Agent协作系统(如CrewAI框架)。多个Agent可以协同完成更复杂的任务,例如一个Agent负责数据收集,另一个负责分析,第三个负责生成报告。
- 增强型Agent(如Plan-and-Execute或Reflexion)。这些框架在ReAct基础上增加了规划和反思步骤,进一步提升了Agent的智能水平。
- 集成实时数据流和边缘计算。通过WebSocket或MQTT协议连接实时数据源,实现更动态的任务执行。
- 开源替代方案,使用Llama3、Mistral等模型本地部署。通过Ollama或llama.cpp等工具,可以在本地运行开源模型,降低成本并保护隐私。
通过本文,读者可掌握从原理到代码的完整路径。





更多硬核网安与AI工具包,请扫码获取完整源码!
希望您的AI Agent开发<|eos|>
更多推荐


所有评论(0)