【AI Agent系列】【MetaGPT】总结这段时间学习MetaGPT的一些学习方法和感悟

简介: 【AI Agent系列】【MetaGPT】总结这段时间学习MetaGPT的一些学习方法和感悟

跟着《MetaGPT智能体开发入门》课程学习了近两周,原本是抱着试试看的心态,没想到自己竟然全程跟了下来。期间踩坑颇多,但也收获颇多,特写个总结回顾一下课程内容和沉淀下自己的收获,同时把我的学习方法记下来,希望后来学习的人能从中获得一点点的灵感或方向。

0. 个人背景

通过标题序号也可能猜出来,下标从0开始,我是一个程序员,不过是C++程序员。

  • Python:能写hello world,零零碎碎的知识,不系统,可以在代码上缝缝补补,但干不了大事。
  • 大模型:刚入门,知道里面的概念(Prompt、Function Calling、Agent等),基本没实操,只会调用OpenAI的一个对话接口(问:OpenAI一共有几个接口😀?)。
  • 爬虫:小白

所以对于本课程,我可能比小白好那么一丢丢,但不多。

1. 我的学习方法

下面说下我的学习方法,这可能不适合所有人,但是希望能对大家有点启发或帮助。

1.1 先跑通demo

教程有示例代码,可以不理解代码的意思,先试着跑通demo。作用有二:

  • 一是心里有底,路通了。既然路通了,结果好坏是有很多方法去调试的(断点也好、日志也罢),就算一行一行运行,也终究能调出大差不差的结果,毕竟demo一般也就不超过百行有效代码。
  • 二是有了成就感。无论懂不懂,我都能看到结果了,这样才有兴趣去深究。

可能有的同学会问demo不通怎么办?

这就考验你的debug问题的能力和运气了。说实话,我也没有很好的办法,只能一点点去debug、搜索、各种试…看过我系列文章的同学都能看出来,我踩得坑真的不少,基本是一步一坑…但是也一步一坑地走了下来。

但无论如何,想尽各种办法跑通示例demo一定是第一步。

1.2 搞清数据流

以我的经验来讲,快速入门了解某段程序最有效的方法,是抓住一个输出,或输入,去捋数据流。你可以看不懂架构的设计,但是一定得知道数据通路

在看数据流的过程,你就会自然而然的知道整个过程涉及哪些模块,每个模块的作用、依赖是什么,从而对整个程序有个宏观的认知。

可以看下我学习过程中绘制的各种图,很丑,但能凑合看出一些东西。

找到自己的画图风格,即使你画的不标准,不适合给别人看,但你能画出来,对程序的理解也是有帮助的。

1.3 有选择地看源码

源码太多,肯定看不过来,也不知道从哪开始看。根据数据流,或者过程中踩得坑,带着问题去看源码最有效

例如:

再比如,下面我要与大家探讨的智能体运行机制,其实就是带着问题去看的。

2. 从一个坑开始,看智能体运行机制

我看这部分的源码的起因,源自第三章作业,打印数字的一个坑。智能体run的时候,必须传入一个字符串,否则不运行,这是当时调试时浪费了我很久时间的一个坑。当时留了个TODO。后面详细了解了下智能体的运行机制,可以看下这篇文章,在这里也简单与大家交流下。

这是官方的智能体运行周期图,从_observe开始,经过思考、行动,最后将结果发送出去。

这是我根据Role的run函数画出来的一个智能体的运行的数据流(欢迎批评指正)。

跟着图,看下源码:

@role_raise_decorator
async def run(self, with_message=None) -> Message | None:
    """Observe, and think and act based on the results of the observation"""
    if with_message:
        msg = None
        if isinstance(with_message, str):
            msg = Message(content=with_message)
        elif isinstance(with_message, Message):
            msg = with_message
        elif isinstance(with_message, list):
            msg = Message(content="\n".join(with_message))
        if not msg.cause_by:
            msg.cause_by = UserRequirement
        self.put_message(msg)
    if not await self._observe():
        # If there is no new information, suspend and wait
        logger.info(f"{self._setting}: no news. waiting.")
        return
    rsp = await self.react()
    # Reset the next action to be taken.
    self.rc.todo = None
    # Send the response message to the Environment object to have it relay the message to the subscribers.
    self.publish_message(rsp)
    return rsp

(1) 首先是对 with_message参数的处理,如果with_message参数不是None,会执行下面指令:

self.put_message(msg)
  • self.put_message(msg)干了什么?
  • 将msg放到自身的msg_buffer中
def put_message(self, message):
        """Place the message into the Role object's private message buffer."""
        if not message:
            return
        self.rc.msg_buffer.push(message)

(2)执行 self._observe()函数,如果返回0或false,会进入if not await self._observe()的条件内,直接return,不触发后续动作的执行。

源码如下:

async def _observe(self, ignore_memory=False) -> int:
        """Prepare new messages for processing from the message buffer and other sources."""
        # Read unprocessed messages from the msg buffer.
        news = []
        if self.recovered: 
            news = [self.latest_observed_msg] if self.latest_observed_msg else []
        if not news:
            news = self.rc.msg_buffer.pop_all()
        # Store the read messages in your own memory to prevent duplicate processing.
        old_messages = [] if ignore_memory else self.rc.memory.get()
        self.rc.memory.add_batch(news)
        # Filter out messages of interest.
        self.rc.news = [
            n for n in news if (n.cause_by in self.rc.watch or self.name in n.send_to) and n not in old_messages
        ]
        self.latest_observed_msg = self.rc.news[-1] if self.rc.news else None  # record the latest observed msg
        # Design Rules:
        # If you need to further categorize Message objects, you can do so using the Message.set_meta function.
        # msg_buffer is a receiving buffer, avoid adding message data and operations to msg_buffer.
        news_text = [f"{i.role}: {i.content[:20]}..." for i in self.rc.news]
        if news_text:
            logger.debug(f"{self._setting} observed: {news_text}")
        return len(self.rc.news)
  • news = self.rc.msg_buffer.pop_all()取出msg_buffer中的所有消息。
  • 重点在这一句代码,从news中筛选出本role关注的消息
self.rc.news = [
         n for n in news if (n.cause_by in self.rc.watch or self.name in n.send_to) and n not in old_messages
     ]
  • 关注的消息:self.rc.watch或者n.send_to
  • watch的内容,可以通过_watch函数设置
def _watch(self, actions: Iterable[Type[Action]] | Iterable[Action]):
        """Watch Actions of interest. Role will select Messages caused by these Actions from its personal message
        buffer during _observe.
        """
        self.rc.watch = {any_to_str(t) for t in actions}

看到这,是不是对刚开始那个必须设置一个msg才能run的坑有了点想法?

  • 没有msg输入,就没有publish_message,_observe函数观察不到信息,就直接return了。

(3)_observe到信息之后,就是思考+动作的react函数了,简单看下,这块还没仔细看,就不讲了,怕误人子弟。

async def react(self) -> Message:
        """Entry to one of three strategies by which Role reacts to the observed Message"""
        if self.rc.react_mode == RoleReactMode.REACT:
            rsp = await self._react()
        elif self.rc.react_mode == RoleReactMode.BY_ORDER:
            rsp = await self._act_by_order()
        elif self.rc.react_mode == RoleReactMode.PLAN_AND_ACT:
            rsp = await self._plan_and_act()
        self._set_state(state=-1)  # current reaction is complete, reset state to -1 and todo back to None
        return rsp

理解了单智能体的运行周期后,很容易理解多智能体间的协作。

看下图(图片来自:https://docs.deepwisdom.ai/main/zh/guide/tutorials/multi_agent_101.html):

其实就是:

(1)每一个Role都在不断观察环境中的信息(_observe函数)

(2)当观察到自己想要的信息后,就会触发后续相应的动作

(3)如果没有观察到想要的信息,则会一直循环观察等待

(4)执行完动作后,会将产生的msg放到环境中(publish_message),供其它Role智能体来使用。

拿我们实现过的例子来看(【AI Agent系列】【MetaGPT】7. 一句话订阅专属信息 - 订阅智能体进阶,实现一个更通用的订阅智能体):

class SubscriptionAssistant(Role):
    """Analyze user subscription requirements."""
    name: str = "同学小张的订阅助手"
    profile: str = "Subscription Assistant"
    goal: str = "analyze user subscription requirements to provide personalized subscription services."
    constraints: str = "utilize the same language as the User Requirement"
    def __init__(self, **kwargs) -> None:
        super().__init__(**kwargs)
        self._init_actions([ParseSubRequirement, RunSubscription]) ## 2. 先解析用户需求,然后运行订阅
        self._watch([UserRequirement, WriteCrawlerCode])  ## 触发

我们实现了一个SubscriptionAssistant的智能体,它_watch了UserRequirement用户消息和WriteCrawlerCode消息。

运行后,它就会_observe环境:

  • 当用户输入信息时,环境中存在了UserRequirement消息,它_observe到了,就会触发后续相应动作。从而实现了与用户的协作。
  • 当其它智能体的WriteCrawlerCode执行完毕,会向环境中写入执行结果的msg,来源(cause_by标记为WriteCrawlerCode),然后SubscriptionAssistant的_observe观察到了,就会触发后续相应动作。从而实现了与其它智能体的协作,也就是多智能体间的协作。

3. 本次课程的收获和感悟

3.1 收获

  • 第一个肯定是 MetaGPT 入门了,对Agent算是有了一个初步的系统的认知。
  • 其次,Python的一些零零散散的知识和用法。比如:
  • 直接在Python中调用系统命令来自动执行程序subprocess(第三章)
  • Python推送微信消息(第四章)
  • Python推送邮箱消息(第四章)
  • GPT写小说的步骤(第五章)
  • 最简单的爬虫程序怎么写(第四章、第五章)

3.2 感悟

  1. MetaGPT目前是一个Agent实现框架,是一个个角色和动作的抽象。要想实现Agent,感觉最重要的还是SOP(标准作业程序),只有有了SOP,才知道怎么定义一个个角色和动作,才知道需要怎么串联每个角色和每个动作。
  2. 目前只是入门,没有具体的需求,所以认识很有限,所以我上面讲的大家选择性的听听即可,希望能给大家一点启发。
  3. 希望后面有需求可以一起讨论学习。
  4. 我也会持续学习MetaGPT教程和源码(官方例子可以开始尝试研究了)。

本文就到这,能力有限,希望大家批评指正。

弱弱地说:欢迎 点赞 + 关注 👏,促使我持续学习,持续干货输出。

+v: jasper_8017 一起交流💬,一起进步💪。微信公众号也可搜【同学小张】 🙏

4. MetaGPT入门系列文章

相关文章
|
3月前
|
机器学习/深度学习 人工智能 自然语言处理
教育领域的AI进展:智能辅导与个性化学习的技术革新与挑战
随着人工智能技术的发展,AI Agent在教育领域的应用日益广泛,特别是在智能辅导与个性化学习方面展现出巨大潜力。通过自然语言处理、机器学习和数据分析等技术,AI可模拟个性化辅导员,根据学生的学习情况提供定制化资源与实时反馈。未来,AI Agent将更注重情感分析与跨学科培养,成为教师的有力助手,推动教育公平与效率提升。然而,数据隐私、个体差异及教育资源不平衡等问题仍需克服,以实现更智能化、全面化的教育生态。
321 10
教育领域的AI进展:智能辅导与个性化学习的技术革新与挑战
|
2月前
|
人工智能 开发框架 搜索推荐
AI Agent构建强大外部工具调用能力不足,MCP Server怎样应对?MCP Serve在企业级Agent系统中的关键意义
本文AI产品专家三桥君探讨了MCP Server在企业级AI Agent系统中的关键作用,通过标准化工具接口实现AI与外部服务的无缝集成。三桥君重点阐述了分布式系统中的会话管理、状态持久化等实践方案,强调MCP Server在降低AI决策风险、提升系统可靠性方面的企业价值,为AI产品经理提供了架构设计与优化策略的实践指导。
250 0
|
3月前
|
人工智能 开发者
阿里云百炼X支付宝:「AI打赏」功能上线,Agent变现更灵活🎉🎉🎉
阿里云百炼平台联合支付宝,推出业内首个Agent「AI打赏」功能,开发者可为应用一键配置赞赏功能,用户打赏金额将直接转入开发者支付宝账户,助力快速变现。
365 1
|
2月前
|
人工智能 自然语言处理 搜索推荐
学霸养成计划:AI如何打造你的专属“学习外挂”?
学霸养成计划:AI如何打造你的专属“学习外挂”?
102 0
|
5月前
|
人工智能 开发框架 决策智能
谷歌开源多智能体开发框架 Agent Development Kit:百行代码构建复杂AI代理,覆盖整个开发周期!
谷歌开源的Agent Development Kit(ADK)是首个代码优先的Python工具包,通过多智能体架构和灵活编排系统,支持开发者在百行代码内构建复杂AI代理,提供预置工具库与动态工作流定义能力。
773 3
谷歌开源多智能体开发框架 Agent Development Kit:百行代码构建复杂AI代理,覆盖整个开发周期!
|
2月前
|
人工智能 算法 关系型数据库
AI编码不是梦:手把手教你指挥Agent开发需求
AI编码不是梦:手把手教你指挥Agent开发需求
994 24
|
2月前
|
人工智能 自然语言处理 API
AI-Compass Agent智能体技术生态:整合AutoGPT、LangGraph、CrewAI等前沿框架,构建自主决策工具调用的AI智能体系统
AI-Compass Agent智能体技术生态:整合AutoGPT、LangGraph、CrewAI等前沿框架,构建自主决策工具调用的AI智能体系统

热门文章

最新文章