@akshay_pachaar: https://x.com/akshay_pachaar/status/2058976178908885210

X AI KOLs Following 工具

摘要

解释了如何通过使用Pydantic模式定义本体来修复代理记忆,实现结构化提取到知识图谱中以进行多跳推理,并提供了一个开源解决方案(Zep)。

https://t.co/VW9EyOiy4Z
查看原文
查看缓存全文

缓存时间: 2026/05/25 18:42

Pydantic 修复了我的 Agent 记忆

你的智能体记了一切,却什么都不懂。

智能体记忆最初基于向量数据库。将事实切分成块,通过相似性检索。

在需要跨块连接事实的查询出现之前,这套方法都工作得很好。一旦出现这种查询,它就崩了。问题不在于相似性,而在于结构。

知识图谱是解决方案。实体作为节点,关系作为边,遍历代替匹配。

但大多数团队遇到了另一堵墙。

当你给智能体一个知识图谱作为记忆时,默认行为是:负责提取的 LLM 自行决定结构。

它自己挑选实体类型、关系标签和属性。

结果是通用的。

举个例子,你在构建一个客户支持智能体。你喂给它 50 条支持对话,涉及客户、工单、功能和升级历史。

你问:“哪些企业客户有未解决的 sev-1 工单?”

图谱里有数据。但每条支持工单都被存成了“主题”节点。每个客户都是“对象”。每条关系都是“关联到”。

无法按类型、严重程度或套餐等级进行筛选。查询返回的是噪音。

智能体没有忘记任何东西。只是没人告诉它该关注什么。

解决方案很直接:预先定义 schema。 告诉提取模型你的领域中存在哪些类型的实体、哪些关系是有效的、每个实体携带哪些属性。

这个组织蓝图被称为 ontology(本体)。你可以把它看作 智能体大脑的 schema

让我们来看看为什么这很重要、没有它会出什么问题,以及如何用一个 100% 开源的方案 来实现它。

为什么平面检索在多跳推理中会失效

基于向量的记忆将事实存为文本块,并通过语义相似性检索。这仅在查询不需要连接不同块中的事实时有效。

考虑一个项目相关的三个事实。

  • Alice 管理 Project Atlas

  • Project Atlas 运行在 PostgreSQL 上

  • PostgreSQL 集群在周二宕机了

一个查询如“Alice 的项目是否受到了周二宕机的影响”需要用到全部三个事实。

向量检索只会检索到事实 1 和 3,因为它们都包含了相关术语。事实 2 是通过 Project Atlas 连接 Alice 和 PostgreSQL 的桥梁,但它既没提到 Alice 也没提到周二。相似性搜索错过了它。

知识图谱将实体存为节点,关系存为边。它不是匹配文本,而是遍历连接。

这条链(Alice → 管理 → Project Atlas → 运行于 → PostgreSQL)正是多跳推理生效的关键,而它在平面向量检索中是看不见的。

记忆流水线与提取步骤的位置

每个基于图的智能体记忆系统都遵循一个通用的流水线:

  • 摄取: 原始数据进入(对话消息、文档、JSON 业务数据)

  • 提取: LLM 读取原始数据,决定存在哪些实体、哪些关系连接它们、哪些属性重要

  • 存储: 提取出的实体变成节点,关系变成边,全部持久化到图中

  • 检索: 查询时,系统搜索图并组装相关事实

  • 交付: 检索到的事实被格式化为上下文块,注入到智能体的 prompt 中

提取步骤决定了所有事情。它决定了你的图里有什么、如何结构化,以及下游可以查询什么。

问题来了。在大多数框架中,这一步是个黑盒。你传入文本,LLM 提取出“实体”和“关系”,你得到节点和边。LLM 自行决定类型、标签和属性。

你无法控制它分类的方式。

让我们看看如何修复。

用 Pydantic 定义 Schema

修复方法跟 AI 栈中其他地方使用的模式一样。

  • FastAPI 端点有 Pydantic 响应模型。

  • 函数调用工具有 Pydantic schema。

  • 在 Zep 中,智能体记忆也是同样的方式。

使用 EntityModel(Pydantic 的 BaseModel 的子类)定义自定义实体类型,配合 EntityText 字段和引导提取模型的描述。

from zep_cloud.external_clients.ontology import EntityModel, EntityText
from pydantic import Field

class Project(EntityModel):
    """
    Represents a specific software project, application, 
    or codebase that the user is building or contributing to.
    """

    project_status: EntityText = Field(
        description="Current status: active, completed, paused, or archived.",
    )
    project_type: EntityText = Field(
        description="Type of project: web app, mobile app, API, CLI tool, etc.",
    )

这里的文档字符串和字段描述非常重要,因为带有具体示例的良好描述能给提取器足够的信号来准确分类。

上面的 Pydantic 描述不只是分类指令。它们教会提取器它原本不认识的词汇。

一个 Technology 实体遵循同样的模式。

class Technology(EntityModel):
    """
    Represents a programming language, framework, library, 
    database, or tool that the user works with.
    """

    tech_category: EntityText = Field(
        description="Category: programming language, framework, database, etc.",
    )

边类型使用 EdgeModel,并携带自己的属性。

from zep_cloud.external_clients.ontology import EdgeModel

class WorksOn(EdgeModel):
    """The user is currently working on, building, or contributing to a project."""
    role: EntityText = Field(
        description="User's role: lead developer, contributor, maintainer, etc.",
    )

class UsesTechnology(EdgeModel):
    """The user actively uses or works with a specific technology."""
    proficiency: EntityText = Field(
        description="Proficiency level: beginner, intermediate, advanced, or expert.",
    )

最后,通过 EntityEdgeSourceTarget 将这些与源/目标约束一起接入图,它定义了哪些实体类型可以通过哪些边类型连接:

from zep_cloud import EntityEdgeSourceTarget

client.graph.set_ontology(
    entities={"Project": Project, "Technology": Technology},
    edges={
        "WORKS_ON": (
            WorksOn,
            [EntityEdgeSourceTarget(source="User", target="Project")],
        ),
        "USES_TECHNOLOGY": (
            UsesTechnology,
            [EntityEdgeSourceTarget(source="User", target="Technology")],
        ),
    },
)

这段代码强制规定:

  • WORKS_ON 只能连接 User 到 Project

  • USES_TECHNOLOGY 只能连接 User 到 Technology

  • 任何不符合这些约束的关系都不会产生类型化边。

总结一下,到目前为止我们得到了:

底层发生了什么

当对话在 schema 激活状态下被摄取时,Zep 的提取管道运行五个步骤:

  • 实体提取 识别文本中的命名实体

  • 实体解析 合并重复项(“Nexus” 和 “Nexus project” 变成一个节点)

  • 事实提取 识别关系并将其输出为类型化边

  • 事实解析 检测矛盾并使过时的事实失效(保留历史)

  • 时间提取 解析时间引用并将其映射到每条边的有效窗口

(插入 GIF)

你的 Pydantic schema 指导步骤 1 和 3。实体类型告诉提取器要寻找什么。带有约束的边类型告诉它要分类哪些关系。解析和时间处理会自动进行。

实际示例演示效果

我们摄取一段对话,其中一位名叫 Alex 的开发者在讨论他的工作(一个名为 Nexus 的活跃 Web 应用、他的技术栈、熟练度):

查询 Project 节点会返回 Nexus,其中填充了 project_statusproject_type 属性。

这个节点不是一个泛泛的“主题”或“对象”。它是一个 Project,带有 schema 中定义的、结构化的字段。

边也是类型化的。

  • WORKS_ON 携带 role: lead developer

  • USES_TECHNOLOGY 对 Python 和 Docker 携带 proficiency: advanced,对 TypeScript 携带 proficiency: intermediate

现在可以按状态筛选项目、按类别筛选技术,并能够准确回答“哪些活跃项目使用了 PostgreSQL”这样的问题。

上下文模板

最后一部分是上下文模板,它将类型化的事实组装成一个可用于 prompt 的块。

你可以定义要包含的边类型和实体类型,Zep 会将其与时间注解一起格式化为一个字符串,注入到智能体的 prompt 中。

client.context.create_context_template(
    template_id="dev-context",
    template="""# PROJECTS
%{edges types=[WORKS_ON] limit=5}

# TECH STACK
%{edges types=[USES_TECHNOLOGY] limit=10}

# PROJECT DETAILS
%{entities types=[Project] limit=5}

# TECHNOLOGIES
%{entities types=[Technology] limit=10}""",
)

效果如下:

生成的上下文块中的每一条都是类型化的、带有时间注解的,并且携带定义的属性。模板只需保存一次,在智能体调用中通过 ID 引用即可。

10/10/10 约束与 Schema 作为推理边界

Zep 强制限制了 10 个自定义实体类型、10 个自定义边类型和每个类型 10 个字段。

这是有意为之,迫使开发者思考领域中的重点,而不是建模所有东西。

源/目标约束也充当了智能体允许记住什么的护栏。如果 schema 中没有包含连接 Project 到 Competitor 的边类型,即使对话中同时提到了两者,提取模型也不会创建该关系。

Schema 定义了有效记忆的空间。

这与类型化函数调用背后的原理相同——我们约束 LLM 的输出空间,使其不能生成无效参数。记忆 schema 将同样的约束应用于智能体存储的内容。

从 3-4 个实体类型和 3-4 个边类型开始,覆盖你 80% 的领域逻辑,然后逐步增加复杂度。

没有 schema 纪律的智能体记忆,就是一个行为像向量存储的图。

某种意义上,你付了构建图的成本,却没有得到结构化检索的好处。

Schema 就是让你找回这个好处的关键,而且由于它是 Pydantic,你没有任何新东西需要学。

对于特定领域的应用尤其如此。LLM 提取在通用知识上做得还可以,但一旦你的领域有内部术语、与常见词冲突的产品名称,或训练数据中缺失的行话,无引导的提取就会产生无意义的结果。Schema 弥补了这个差距。它将领域词汇直接带入提取步骤,LLM 不需要事先见过你的术语。它只需要你写的定义。

你可以在这里找到 Zep 的 GitHub 仓库 → (别忘了给星 🌟)

感谢阅读!

相似文章

Zep:一种用于智能体记忆的时序知识图谱架构

Papers with Code Trending

本文介绍了 Zep,这是一种用于智能体(agent)记忆的时间知识图谱架构,在 DMR 和 LongMemEval 等基准测试中表现优于 MemGPT。文章强调了 Zep 在企业级用例中处理动态知识融合和时间推理的能力。

@ByteMohit: https://x.com/ByteMohit/status/2063493300884246598

X AI KOLs Timeline

一篇关于构建AgentForge的详细技术文章,AgentForge是一个基于Python的开源agent框架,涵盖了会话运行时、工具合约、审批层和持久化等组件,强调agent由其运行时定义,而不仅仅是模型。