前端进阶之旅前端进阶之旅
基础篇
进阶篇
高频篇
精选篇
手写篇
面经篇
AI 篇
原理篇
每日一题
小程序题库
知识卡片
  • 场景篇按分类整理的大前端场景考点
  • 历年面经按年份追踪真实考点
  • 算法题库NEW在线编码即时判题
  • 专项自测100 题快速查漏
  • 前端基础
    • HTTP从报文一路讲到 HTTPS
    • 浏览器渲染、事件循环、进程
    • 计算机基础Linux、网络、操作系统
  • 进阶专项
    • 设计模式23 种模式怎么用
    • 前端系统进阶学习大型项目工程化
    • 前端综合文章长期沉淀的实践文
  • 工程与工具
    • Node学习指南从环境搭建到服务端
    • NPM工作流script、依赖与发布
    • Docker容器化部署上手
    • Canvas图形与动画实战
  • 路线与导图
    • 思维导图知识点全景图
    • 学习路线按图索骥不跑偏
  • 动态
    • 公众号动态公众号历史文章
    • 博客动态站长的技术博客
    • 开发者导航常用工具与文档站
  • AI 助手随时提问,即时解析
  • AI 模拟面试模拟真实面试 + 报告
  • AI 知识地图串起全站知识点
  • AI 定制路线按你的简历现排
AI 热点
旧版
基础篇
进阶篇
高频篇
精选篇
手写篇
面经篇
AI 篇
原理篇
每日一题
小程序题库
知识卡片
  • 场景篇按分类整理的大前端场景考点
  • 历年面经按年份追踪真实考点
  • 算法题库NEW在线编码即时判题
  • 专项自测100 题快速查漏
  • 前端基础
    • HTTP从报文一路讲到 HTTPS
    • 浏览器渲染、事件循环、进程
    • 计算机基础Linux、网络、操作系统
  • 进阶专项
    • 设计模式23 种模式怎么用
    • 前端系统进阶学习大型项目工程化
    • 前端综合文章长期沉淀的实践文
  • 工程与工具
    • Node学习指南从环境搭建到服务端
    • NPM工作流script、依赖与发布
    • Docker容器化部署上手
    • Canvas图形与动画实战
  • 路线与导图
    • 思维导图知识点全景图
    • 学习路线按图索骥不跑偏
  • 动态
    • 公众号动态公众号历史文章
    • 博客动态站长的技术博客
    • 开发者导航常用工具与文档站
  • AI 助手随时提问,即时解析
  • AI 模拟面试模拟真实面试 + 报告
  • AI 知识地图串起全站知识点
  • AI 定制路线按你的简历现排
AI 热点
旧版
返回 AI 情报前线
All News · 全部资讯9309
  • DeepSeek V4 Pro GA 评测:推理 token 减少 18-62%,JSON 提取终于可靠
  • tracelint:用静态分析检测 Agent 工具调用失败
  • Agent安全第三轴:身份与授权之外的工具安全
  • crewai-go v0.4.0:Go语言多Agent编排框架量产就绪
  • PromptShrink:生产级Prompt压缩工具,省60%Token
  • 多模型 Node.js 路由架构深度对比
  • AI 编程 Agent 正在走出 IDE
  • GPT-5.6 Sol API 价格下调 50%
  • AI 编程的边界:代码能跑≠系统可维护
  • 以色列疑似利用虚假智库诱导AI聊天机器人
  • GitHub Actions绿色不等于发布成功
  • AI 修复工具引入漏洞,另一 AI 自主发现并利用
  • Snowflake CLI 与 OpenHands 高危漏洞预警
  • Claude 新增生产语音 Agent 管理和删除功能
  • AI;DR:程序员视角审视AI阅读工具的局限
  • 同集群利用率提升33点:调换任务顺序就够了
  • AI Agent应锁定工具契约而非仅工具名
  • Vercel发布Agent Plugins 1.0:AI Agent互操作标准成型
  • robots.txt 对 AI 爬虫的屏蔽效果:你可能误读了 RFC 9309
  • 15 款 AI API 真实延迟横评:150 次测试揭示实际响应速度
  • 给 AI Agent 加记忆模块避免重复踩坑
  • 五个程序员必知的Prompt管理工具
  • 5 款值得关注的 Prompt 管理工具评测
  • 我把AI API费用削减了95%的真实经验
  • 我的 AI API 账单如何降低了 95%(质量不降)
  • 免费模型端点上线 CI 前必做的 5 项检查
  • MiniMax 开源音乐生成模型:一次生成 5 分钟完整歌曲
  • 用哈希链审计免费 LLM 模型输出:防止响应篡改
  • Tracewood:将 AI 编码 Agent 遥测数据变为 3D 森林可视化
  • 私有知识库 Node.js 应用的多模型路由计费设计
  • NVIDIA 30B MoE 模型登陆 SageMaker:Agent 任务吞吐量提升 4 倍
  • xAI + Cursor 联合推出 Grokbot:云端操控电脑的 AI Agent 体验评测
  • 2025 本地优先 AI Agent 实战总结:ScreenPipe、Headroom 与隐私代价
  • AI Agent 上线前必须回答的权限设计问题
  • 2026年AI模型延迟实测:TTFT与吞吐量全排行
  • Circle推出AI Agent应用商店:机器间支付发现成为竞争壁垒
  • 从零构建 Agentic AI 系统:混合 RAG、GraphRAG、12 工具与 K8s 部署
  • AI Agent 监控的实战教训:空输出比报错更难发现
  • TokenCap 2.1:AI 编码助手的上下文压缩与 Debt Ledger
  • Qwen3.8-27B 基准测试逼近 DeepSeek V4 与 GPT-5.6 Luna Max
  • AI Agent 测试范式转变:从验证代码到评估行为
  • LLM 路由指南:按任务选对模型
  • 2026年AI Agent实战指南:选型核心维度与架构对比
  • 付费沙箱中 AI Agent 的隐性计费陷阱
  • 免费模型端点 ≠ 免费服务器:四层对比选型框架
  • Amodei反驳开源AI:开放权重并非万能解
  • Replit 引入黑盒渗透测试强化 AI 应用安全
  • 生产级 LLM 记忆系统实战设计
  • 本地 LLM 每 Token 成本估算指南
  • 实测10款编程LLM生产级负载表现
  • 用 OpenClaw + Bedrock AgentCore 让 AI Agent 自主支付外部 API
  • 已加载 51 / 9309
8.0
热点
AI SCORE
编程提效2026-08-18 03:07

给 AI Agent 加记忆模块避免重复踩坑

dev.to · AI#AI Agent#Mem0#工程实践
Editor brief · 编辑速览

通过 Mem0 为 AI Agent 添加记忆层,在工具调用前查询历史失败记录防止重蹈覆辙,调用后记录结果形成闭环,提供可运行的 MemoryGatekeeper 实现。

文章思维导图
Knowledge map
拖拽缩放
Full translation

完整中文译文

你的 AI Agent 调用了一个不稳定的 API,得到 429 错误,用同样的参数重试,再次触发限流。十分钟后,在一个新的会话中,它做了完全相同的事。失败的经历什么都没被记住——Agent 无法知道它已经学到了这个教训,因为这段"教训"存在于一个随进程退出就被丢弃的 transcript 中。

本周,一篇关于手动 gatekeeping AI Agent 工具调用的帖子登上了 dev.to 首页,收到了 48 条评论——大多是开发者们在争论你对 Agent 的 tool-calling 循环能有多大信任度。老实说:你能信任它的程度,取决于它记住了多少已经出错过的经历。下面是一个完整的、可运行的 gatekeeper实现,它封装了任意工具调用,在执行前检查 Mem0 中相似的过往失败记录,并在之后将结果写回内存——这样当你的 Agent 第二次要犯同样的错误时,它就知道了。

一个 MemoryGatekeeper 类,位于 Agent 决定调用工具和实际执行之间:

在调用工具前,搜索语义上相似的过往尝试记录。

如果相似的尝试最近失败过,阻止这次调用,并返回记忆中的原因,而不是浪费一次真实的 API 调用。

每次调用后——无论成功还是失败——将结果写回内存。

你会运行同一个脚本两次:第一次运行失败并被记录,第二次运行在浪费请求前就被拦截了。

你需要 Python 3.10+、一个 OpenAI API key(Mem0 的默认提取管道用它把原始文本转化为结构化记忆——这个本地设置不需要单独的 Mem0 账户)和 mem0ai 包。

pip install mem0ai
export OPENAI_API_KEY=sk-...

Mem0 默认使用本地磁盘向量存储,所以这里的任何操作都不会与托管版 Mem0 服务通信——它是一个完全自包含的、属于你自己的记忆层。

第一步:gatekeeper

# gatekeeper.py
from mem0 import Memory
from datetime import datetime, timezone

class MemoryGatekeeper:
    def __init__(self, agent_id="default-agent", block_threshold=0.75):
        self.memory = Memory()
        self.agent_id = agent_id
        self.block_threshold = block_threshold

    def _describe_call(self, tool_name, args):
        return f"tool call: {tool_name} with args {args}"

    def check(self, tool_name, args):
        """Returns (allowed: bool, reason: str | None)."""
        query = self._describe_call(tool_name, args)
        hits = self.memory.search(query, user_id=self.agent_id, limit=3)

        for hit in hits.get("results", []):
            score = hit.get("score", 0)
            memory_text = hit.get("memory", "")
            if score >= self.block_threshold and "failed" in memory_text.lower():
                return False, memory_text
        return True, None

    def record(self, tool_name, args, success, detail):
        outcome = "succeeded" if success else "failed"
        text = (
            f"{self._describe_call(tool_name, args)} {outcome} "
            f"at {datetime.now(timezone.utc).isoformat()}: {detail}"
        )
        self.memory.add(text, user_id=self.agent_id)

    def call(self, tool_name, args, fn):
        allowed, reason = self.check(tool_name, args)
        if not allowed:
            print(f"[BLOCKED] {tool_name}({args}) — remembered: {reason}")
            return {"blocked": True, "reason": reason}

        try:
            result = fn(*args.values()) if isinstance(args, dict) else fn(args)
            self.record(tool_name, args, True, "ok")
            return {"blocked": False, "result": result}
        except Exception as exc:
            self.record(tool_name, args, False, str(exc))
            raise

check 步骤使用的是语义搜索而非精确字符串匹配——fetch_weather(city="NYC") 和 fetch_weather(city="New York") 会相互匹配,这正是精确匹配缓存会漏掉的那类近似重复。

第二步:一个可预测地失败的工具

# flaky_tool.py
class RateLimitError(Exception):
    pass

def call_flaky_api(endpoint):
    if endpoint == "/reports/daily":
        raise RateLimitError("429: rate limit exceeded, retry after 3600s")
    return {"status": "ok", "endpoint": endpoint}
# run.py
from gatekeeper import MemoryGatekeeper
from flaky_tool import call_flaky_api

gate = MemoryGatekeeper(agent_id="report-agent")

try:
    gate.call("call_flaky_api", {"endpoint": "/reports/daily"}, call_flaky_api)
except Exception as exc:
    print(f"First attempt failed as expected: {exc}")
First attempt failed as expected: 429: rate limit exceeded, retry after 3600s

再次运行 python run.py——同一个进程、同样的工具、同样的参数,但现在 Agent 有了之前失败的记忆:

[BLOCKED] call_flaky_api({'endpoint': '/reports/daily'}) — remembered: tool call: call_flaky_api with args {'endpoint': '/reports/daily'} failed at 2026-08-18T09:12:04+00:00: 429: rate limit exceeded, retry after 3600s

没有第二次 API 调用,没有第二次限流触发,而且 Agent 得到了一个它可以推理(或转发给人类)的理由,而不是一个原始的堆栈跟踪。

调优以适配真实使用

一旦你超越玩具示例,有三个旋钮值得关注:

block_threshold — 0.75 是刻意保守的设置。调低它,你会拦截那些本来可能成功的近似请求;调高它,你只会捕获几乎完全相同的重复。信任默认值之前,先记录一周的所有拦截决策。

按 Agent 作用域管理记忆,而不是全局。 user_id=self.agent_id 可以防止一个 Agent 的坏运气阻塞另一个 Agent 对同一工具的合法调用。如果多个 Agent 确实共享风险(同一个下游 API、同一限流 bucket),给它们一个共享的 agent_id。

让失败过期,不要永久保留。 一小时前的 429 应该阻止重试;三周前的 429 可能就不应该了。Mem0 的记忆在其 metadata 中携带时间戳——在 check() 中添加一个检查,丢弃超过重试窗口的命中(例如 time.time() - hit["created_at"] < 3600),这样陈旧的失败就不会永久禁用一个已经恢复的工具。这一行过滤逻辑,是 gatekeeper 和"害怕所有它曾经失败过的一切"的 Agent 之间的区别。

为什么这比进程内缓存更好

一个普通的 dict 或 functools.lru_cache 可以在单次运行中捕获完全重复的情况,但它随进程消亡,而且无法做语义匹配——它不会知道重试 /reports/daily 和 /reports/daily/ 是同一个错误。将这个路由到 Mem0 的特别价值在于:记忆在重启和部署之间持久化,而且同一个存储也可以保存成功的模式——成功过的工具调用、格式良好的参数、成功完成的序列——所以这个 gatekeeper 不只是一个黑名单,它是一个 Agent 的开端——这个 Agent 会随着时间真正学会更好地使用它的工具,而不是每次冷启动都重新学习同样的教训。

上面的完整示例不到 80 行,只需要一个 Python 环境和 OpenAI key 就能运行——克隆它,运行两次,在你还没读完这句话之前就会看到拦截实时发生。

Original source

本文由 AI 翻译整理自 dev.to · AI,原文版权归原作者所有。

阅读英文原文
上一篇
15 款 AI API 真实延迟横评:150 次测试揭示实际响应速度
下一篇
五个程序员必知的Prompt管理工具