什么是 Agent 的 Message

发布于:2025-05-22 ⋅ 阅读:(19) ⋅ 点赞:(0)

Messages

2.4.1 概述

什么是 Agent 的 Message?

当你和朋友聊天、在网上搜索信息或是对手机语音助手说“帮我查一下天气”时,其实你都在向某个“代理者(Agent)”发送一条“信息(Message)”。这里的“代理者”既可以是一个人,也可以是一个能执行指令的智能程序或系统,而“信息”则是你传递的指令、问题或数据。在日常生活中,这种信息交互常常不易察觉,但在计算机科学、人工智能和自动化任务中,“Agent的Message”是一个至关重要的基础概念。

简单来说,Agent的Message就是指系统中“智能体”或“代理者”之间互相传递的指令或数据包。就好比你给朋友发一条微信消息请他帮忙带杯咖啡,在智能系统中,“Agent”则是那些负责完成任务的角色,而“Message”则是他们沟通和协作的工具。当一个Agent收到Message后,会根据内容做出决策、执行任务或回复信息。

在 CAMEL 系统中,BaseMessage 是所有消息对象的基础类,它为对话中的每一条信息提供了统一的结构和标准化的处理方式。无论是用户输入的一段文本,还是包含图片、视频等多模态信息的数据包,都可以通过 BaseMessage 来统一表示和管理。

为什么需要统一的消息结构?

在一个对话系统中,消息可能来自多方(如用户、系统、不同类型的 Agent),且信息内容不局限于纯文本,还可能包括图像、视频甚至是自定义的元数据(metadata)。如果没有一个统一的基础类来约束这些消息的格式,开发者就会面临如下问题:

  • 类型繁杂且难以维护:不同消息类型需要各自的代码逻辑和数据结构,导致系统复杂度提高。

  • 难以扩展和对接:当需要增加新类型的消息(如引入新媒体格式或上下文信息)时,很可能需要大幅度修改原有代码。

  • 通用处理困难:缺乏统一结构会让调试、日志记录和分析对话信息变得更加麻烦。

通过使用 BaseMessage,你可以:

  • 将消息的创建、变形(如格式转换)和传递标准化。

  • 简化对消息类型的扩展,提高代码的可维护性和可读性。

  • 为后续的功能模块(如消息过滤、路由、多轮对话管理)提供一个统一的数据基础。

并且熟练掌握Message相关内容,对我们后续无论是做RAG应用或者模型的Fine-tune都非常重要!在后续章节我们会为大家介绍。

2.4.2 创建和使用Message

在了解了 BaseMessage 存在的意义后,让我们直接通过实例化来看看如何创建和使用它。通过一个最小化示例,我们将掌握 BaseMessage 的关键属性和基本用法,再进一步扩展到多模态内容。

创建 BaseMessage 实例的最小化示例

下面是一个最基本的代码示例,将创建一条来自用户的文本消息:

from camel.messages import BaseMessage
from camel.types import RoleType

# 创建一个简单的用户消息
message = BaseMessage(
    role_name="example_user",
    role_type=RoleType.USER,
    content="Hello, CAMEL!",
    meta_dict={} #添加必需的meta dict参数,即使为空也要提供,否则会报 TypeError
)

print(message)

>>>
BaseMessage(role_name='example_user', role_type=<RoleType.USER: 'user'>, meta_dict={}, content='Hello, CAMEL!', video_bytes=None, image_list=None, image_detail='auto', video_detail='low', parsed=None)

在上述示例中,我们创建了一条来自 example_user 的 USER 类型消息,内容为纯文本 "Hello, CAMEL!"。这就是一个最小化的 BaseMessage 示例。

关键属性介绍

  • role_name:给消息一个容易辨识的名称,如 "User""Assistant""System"。在更复杂的场景中,你或许会有多个用户、多个 Agent,通过 role_name 能帮助你追踪消息来源。

  • role_type:角色类型一般来自 RoleType 枚举,以明确此消息在对话中的身份。例如:

    • RoleType.USER:表示该消息来自用户

    • RoleType.ASSISTANT:表示该消息来自智能助手

  • content:消息的核心载体,一般是文本,也可能是解析指令、问题描述或描述性文字。

简单扩展:添加多模态内容

除了纯文本外,BaseMessage 还支持包含图片、视频等多模态信息。这可以为你的对话系统带来更丰富的交互体验。下面的示例展示了如何向 BaseMessage 添加一张图片。假设你已将一张图片加载为 PIL.Image 对象:

from PIL import Image
from io import BytesIO
import requests

# 下载一张图片并创建一个 PIL Image 对象
url = "https://raw.githubusercontent.com/camel-ai/camel/master/misc/logo_light.png"
response = requests.get(url)
img = Image.open(BytesIO(response.content))

# 创建包含图片的用户消息
image_message = BaseMessage(
    role_name="User_with_image",
    role_type=RoleType.USER,
    content="Here is an image",
    meta_dict={},
    image_list=[img]  # 将图片列表作为参数传入
)

print(image_message)

>>>
BaseMessage(role_name='User_with_image', role_type=<RoleType.USER: 'user'>, meta_dict={}, content='Here is an image', video_bytes=None, image_list=[<PIL.PngImagePlugin.PngImageFile image mode=RGBA size=3520x720 at 0x1DDFF8E88F0>], image_detail='auto', video_detail='low', parsed=None)

同理,如果你有视频数据(如 video_bytes),也可将视频信息传入 BaseMessage。当你的消息中包含图片、视频等丰富媒体信息时,后续的组件(如 ChatAgent)便可利用这些多模态数据进行更智能和灵活的响应。

2.4.3 不同类型消息的处理

在使用 BaseMessage 的过程中,你不仅可以轻松创建基本的用户消息,也能够通过其内置方法快速生成其它类型(如系统消息、助手消息)的实例,并对其内容进行更新和转换。此外,BaseMessage 提供了多种便利的转换方法,可将消息转化为不同格式,便于对接诸如 OpenAI 等后端服务。

快速生成不同类型的消息

通过 BaseMessage 的类方法,我们可以快捷创建出用户(User)、助手(Assistant)的消息:

from camel.messages import BaseMessage

# 创建用户消息
user_msg = BaseMessage.make_user_message(
    role_name="User_1",
    content="Hi, what can you do?"
)

# 创建助手消息
assistant_msg = BaseMessage.make_assistant_message(
    role_name="Assistant_1",
    content="I can help you with various tasks."
)

print("User Message:", user_msg)
print("Assistant Message:", assistant_msg)

在上述示例中,你无需再手动指定 role_type,使用这些类方法即可轻松创建特定角色的消息。这样有助于在你的应用中保持代码整洁和可读性。

更新消息内容

有时你需要基于某条原有的消息创建略有改动的新消息。BaseMessage 提供了 create_new_instance() 方法,使你能在保持原消息基础信息的同时,轻松更新 content

# 基于用户消息创建一个新消息,内容稍作修改
updated_user_msg = user_msg.create_new_instance("Hi, can you tell me more about CAMEL?")
print("Updated User Message:", updated_user_msg)

这个方法非常有用,可以在对话过程中根据上下文动态构建消息流,而无需从头创建所有参数。

将消息转换为字典格式

如果你需要查看消息内部结构,或者将消息数据传给其它系统、序列化保存,BaseMessageto_dict() 方法可以直接将消息对象转化为字典结构:

msg_dict = assistant_msg.to_dict()
print("Message as dict:", msg_dict)

输出的字典中会包含消息的 role_namerole_typecontent 等信息,使得你可以轻松与其它数据处理流程对接。

适配 OpenAI 后端的消息格式

在实际应用中,你可能需要将消息传给 OpenAI 的对话接口。BaseMessage 提供了一组方法来将现有消息快速转化成符合 OpenAI 后端需求的格式。例如:

from camel.types import OpenAIBackendRole

# 将用户消息转化为OpenAI后端兼容的用户消息
openai_user_msg = user_msg.to_openai_message(role_at_backend=OpenAIBackendRole.USER)
print("OpenAI-compatible user message:", openai_user_msg)

# 将助手消息转化为OpenAI后端的助手消息
openai_assistant_msg = assistant_msg.to_openai_assistant_message()
print("OpenAI-compatible assistant message:", openai_assistant_msg)

通过这些方法,你可以轻松地将 BaseMessage 对象接入到 OpenAI 接口的调用流程中,无需手动编写繁琐的转换逻辑。

2.4.4 与ChatAgent协作

在前面的小节中,我们学习了如何创建和操作 BaseMessage。现在,让我们把所学的知识付诸实践,将这些消息交给 ChatAgent,让对话真正“活”起来。

ChatAgent 是 CAMEL 系统中负责对话处理与智能回应的组件。当你将 BaseMessage 对象传递给 ChatAgent 时,ChatAgent 将根据系统和用户消息的内容,生成具有上下文感知的回复。

将文本消息直接交给 ChatAgent 的基本用法

如果你仅想与智能助手进行一段简单的对话,可以直接构造一个文本类型的用户消息,并使用 ChatAgentstep() 方法进行响应,在实际使用过程中,我们无需严格按照BaseMessage的格式来设置我们的message,ChatAgent会通过make_assistant_message等方法会将字符串格式的msg转换成BaseMessage,我们只需要用最简便的字符串来设置我们message,当然,如果你对role_name和role_type有特殊要求的话,也可以按照BaseMessage的格式来设置message:

from camel.agents import ChatAgent
from camel.models import ModelFactory
from camel.types import ModelPlatformType
import os
from dotenv import load_dotenv

load_dotenv()
api_key = os.getenv('QWEN_API_KEY')

model = ModelFactory.create(
    model_platform=ModelPlatformType.OPENAI_COMPATIBLE_MODEL,
    model_type="Qwen/Qwen2.5-72B-Instruct",
    url='https://api-inference.modelscope.cn/v1/',
    api_key=api_key
)

# 创建系统消息,告诉ChatAgent自己的角色定位
system_msg = "You are a helpful assistant that responds to user queries."

# 实例化一个ChatAgent
chat_agent = ChatAgent(model=model, system_message=system_msg,output_language='zh')

# 构造用户消息
user_msg = "Hello! Can you tell me something about CAMEL AI?"

# 将用户消息传给ChatAgent,并获取回复
response = chat_agent.step(user_msg)
print("Assistant Response:", response.msgs[0].content)

>>>
Assistant Response: 当然可以!CAMEL AI 是一个先进的语言模型,它被设计用来进行多轮对话、理解复杂指令并生成高质量的文本。这个模型能够处理各种任务,比如回答问题、撰写文章、创作故事等。CAMEL AI 的目标是通过自然语言处理技术,为用户提供更加智能和人性化的交互体验。如果你有任何具体的问题或需要帮助的地方,欢迎随时告诉我!

在该示例中,我们先为 ChatAgent 提供一个系统消息指定它的身份,然后发送用户文本消息,最终获得智能助手的文本回复。

使用 BaseMessage 传递更丰富的上下文和多模态信息给 ChatAgent

BaseMessage 不仅可用于传递纯文本,还可扩展为多模态消息。当你在对话中加入图片、视频或自定义元数据时,ChatAgent 有机会根据这些额外信息提供更有针对性的回答。例如,在发送消息时,你可以在 BaseMessage 中包含图片列表或自定义的 meta_dict 信息,帮助 ChatAgent 理解上下文或额外提示:

from camel.messages import BaseMessage
# 在用户消息中添加元数据
user_msg_with_meta = BaseMessage.make_user_message(
    role_name="User",
    content="Here is some extra context in the metadata.",
    meta_dict={"processing_time": 1.23, "api_version": "v2", "user_id": "1234567890"}
)

response_with_meta = chat_agent.step(user_msg_with_meta)
print("Assistant Response with metadata:", response_with_meta.msgs[0].content)

>>>
Assistant Response with metadata: 了解了!如果您能提供更多关于元数据的具体信息或上下文,我可以更好地帮助您解答或处理相关问题。请告诉我您需要了解什么方面的内容?

在此示例中, meta_dict 主要用于系统内部,而不是直接的模型交互。可以在复杂的对话系统中进行消息路由和状态管理。

# 展示消息的元数据和内容
print("=== 消息元数据信息 ===")
print(f"用户ID: {user_msg_with_meta.meta_dict['user_id']}")
print(f"API版本: {user_msg_with_meta.meta_dict['api_version']}")
print(f"处理时间: {user_msg_with_meta.meta_dict['processing_time']}秒")

>>>
=== 消息元数据信息 ===
用户ID: 1234567890
API版本: v2
处理时间: 1.23

实际案例:发送图片并获取智能回复

下面让我们演示一个更完整的用例:发送一张图片给 ChatAgent,让它根据图片内容进行描述或回答相关问题。这可以用于场景如:让智能助手识别图像中的物体、提取图像信息,或者对图片进行描述。

from camel.agents import ChatAgent
from camel.messages import BaseMessage
from camel.models import ModelFactory
from camel.types import ModelPlatformType,RoleType

from io import BytesIO
import requests
from PIL import Image
import os
from dotenv import load_dotenv

load_dotenv()
api_key = os.getenv('QWEN_API_KEY')

model = ModelFactory.create(
    model_platform=ModelPlatformType.OPENAI_COMPATIBLE_MODEL,
    model_type="Qwen/QVQ-72B-Preview",
    url='https://api-inference.modelscope.cn/v1/',
    api_key=api_key
)

# 实例化ChatAgent
chat_agent = ChatAgent(model=model,output_language='中文')

# 图片URL
url = "https://img0.baidu.com/it/u=2205376118,3235587920&fm=253&fmt=auto&app=120&f=JPEG?w=846&h=800"
response = requests.get(url)
img = Image.open(BytesIO(response.content))

user_image_msg = BaseMessage.make_user_message(
    role_name="User", 
    content="请描述这张图片的内容", 
    image_list=[img]  # 将图片放入列表中
)

# 将包含图片的消息传给ChatAgent
response_with_image = chat_agent.step(user_image_msg)
print("Assistant's description of the image:", response_with_image.msgs[0].content)

在这个案例中,当 ChatAgent 接收到包含图片的消息后,它将尝试根据自身的知识和处理能力对图片进行描述。此示例展示了多模态消息传递的潜力,让智能对话系统能处理不仅仅是文本的信息。

2.4.5 Responses

Agent(Agent)在与用户交互的过程中,会根据用户的输入生成相应的响应。这些响应不仅包含要显示给用户的消息,还可能包含额外的信息,如会话状态、上下文数据等。camel.responses 模块是 CAMEL 框架中处理聊天Agent响应的重要部分。其中ChatAgentResponse 类用于封装聊天Agent(ChatAgent)的交互输出,结构化响应内容,便于开发者访问消息、会话状态等信息。

一个典型的Agent响应通常包括以下几个部分:

  • 消息内容(Message Content):这是用户直接看到的部分,如文本、图片等。

  • 会话状态(Session Status):指示会话是否继续、结束或需要进行其他操作。

  • 附加信息(Additional Information):用于存储上下文数据、调试信息或其他辅助数据。

ChatAgentResponse 的类属性包括:

  • msgs:一个包含 BaseMessage 对象的列表,表示Agent生成的消息。根据模式的不同,列表内容会有所不同:

    • 空列表:表示消息生成时出现错误。

    • 单条消息:表示正常的消息生成操作。

    • 多条消息:表示Agent处于“批评者模式”(critic mode)。

  • terminated:一个布尔值,指示聊天会话是否已经被Agent终止。

  • info:一个字典,包含与会话相关的附加信息,例如使用统计或工具调用信息。

以下代码展示如何使用 ChatAgentResponse 类:

from camel.responses import ChatAgentResponse
from camel.messages import BaseMessage
from camel.types import RoleType

# 创建一个 ChatAgentResponse 实例
response = ChatAgentResponse(
    msgs=[
        BaseMessage(
            role_name="Assistant",  # 助手的角色名称
            role_type=RoleType.ASSISTANT,  # 指定角色类型
            content="你好,我可以帮您做什么?",  # 消息内容
            meta_dict={}  # 提供一个空的元数据字典(可根据需要填充)
        )
    ],  
    terminated=False,  # 会话未终止
    info={"usage": {"prompt_tokens": 10, "completion_tokens": 15}}  # 附加信息
)

# 访问属性
messages = response.msgs  # 获取Agent生成的消息
is_terminated = response.terminated  # 会话是否终止
additional_info = response.info  # 获取附加信息

# 打印消息内容
print("消息内容:", messages[0].content)
# 打印会话是否终止
print("会话是否终止:", is_terminated)
# 打印附加信息
print("附加信息:", additional_info)

>>> 消息内容: 你好,我可以帮您做什么?
>>> 会话是否终止: False
>>> 附加信息: {'usage': {'prompt_tokens': 10, 'completion_tokens': 15}}

camel.responses 包为Agent的响应提供了一个结构化和规范化的方式。通过使用 ChatAgentResponse 类,开发者可以确保所有响应都符合预期的格式,并且易于扩展和维护。

2.4.6 实践练习

经过本章的学习,你已经了解到 BaseMessage 在 CAMEL 系统中的定位与重要性。从基本的文本消息,到包含图片、元数据的多模态消息,再到如何将这些消息与 ChatAgent 进行整合,本章为你搭建了一个基础框架,让你能自如地操控消息流。以下是一些可以尝试的探索方向。

  1. 扩展消息属性
    创建一个用户消息,并在 meta_dict 中增加若干条元数据(如用户偏好、语言设置等)。将该消息传递给 ChatAgent,观察系统在回答中是否有所变化。

  2. 多轮对话场景
    使用 BaseMessage 连续发送多条用户消息,模拟多轮对话。比如,先询问 CAMEL 的用途,然后再根据回复提出后续问题,看看 ChatAgent 是否能保持上下文连贯。

  3. 多模态信息尝试
    尝试传入不同图片或使用 image_detail 等参数,观察 ChatAgent 的回答变化。可以试试让 ChatAgent 对比两张不同的图片,并描述区别。

  4. 与 OpenAI 接口整合(可选,进阶挑战):
    将生成的 BaseMessage 转为 OpenAI 后端可用的消息格式,然后使用 OpenAI 的 ChatCompletion 接口来获取答案。比较一下与 ChatAgent 内部实现的响应有何不同。


网站公告

今日签到

点亮在社区的每一天
去签到