RDS长期记忆

更新时间:
复制为 MD 格式

本文介绍了阿里云RDS长期记忆,一个为AI应用提供跨会话、个性化记忆能力的企业级解决方案。文档详细说明了如何通过阿里云RDS mem0ai SDK快速接入服务,并提供了创建、搜索、删除记忆等核心操作的完整API参考。

背景介绍

在大语言模型(LLM)驱动的AI应用时代,记忆能力(AI Memory)正在成为决定用户体验和应用价值的核心要素。传统的AI应用往往是“无状态”的(每次交互都是独立的),模型无法记住用户的偏好、历史对话和个性化需求。这种模式导致了三个关键问题:

  • 上下文丢失:用户需要在每次对话中重复说明自己的背景和需求。

  • 个性化缺失:AI无法根据用户的长期行为模式提供定制化服务。

  • 成本高昂:为保持上下文,应用不得不传递大量历史对话,导致Token消耗激增。

阿里云RDS长期记忆是一款基于开源项目Mem0打造的企业级AI记忆增强解决方案。它通过智能化的记忆管理,让AI应用能够跨会话保持上下文、随时间自适应学习,并智能地存储和检索相关信息,帮助您构建具备“长期记忆”的下一代个性化AI应用。

功能优势

功能优势

描述

统一混合存储架构

深度整合阿里云RDS PostgreSQL,利用其强大的扩展生态,实现向量、图、关系型数据的“三位一体”存储。在一个数据库实例中统一管理所有记忆数据,极大简化了AI应用的后端架构。

企业级向量检索引擎

内置高性能的pgvector扩展,提供企业级的向量存储与检索能力。支持HNSW、IVFFlat等多种索引算法和余弦相似度、欧氏距离等多种距离度量,并可将向量搜索与SQL条件过滤无缝结合,实现灵活高效的混合查询。

原生图数据库能力

集成 Apache AGE(A Graph Extension)扩展,使RDS PostgreSQL具备完整的图数据库功能。支持与Neo4j兼容的Cypher查询语言,可自动从对话中提取实体与关系,构建知识图谱,实现更深层次的记忆关联与推理。所有操作均符合ACID事务保证。

兼容开源,无缝集成

方案基于广开源AI记忆层项目 Mem0 构建,兼容其APISDK。您可以利用简洁的接口快速将记忆能力集成到现有应用中,或将本地的Mem0应用平滑迁移至云上。

应用场景

基于其强大的长期记忆和关系推理能力,RDS长期记忆适用于以下场景:

  • 个性化智能助理:记住用户的个人信息(如姓名、职业)、偏好(如“喜欢辣的食物”)和历史指令,提供更贴心、更懂你的互动体验。

  • 多轮对话客服:在长时间、跨会话的客户支持中,完整记录问题的上下文和历史解决方案,避免让用户重复描述问题,提升解决效率。

  • 知识密集型AI应用:在教育、研究、法律咨询等领域,帮助AI构建和沉淀特定领域的知识图谱,实现基于知识的智能问答和推理。

  • 复杂关系分析:在团队协作、项目管理等场景中,记录人与人、人与事之间的关系(如“李四是张三的导师”),为决策提供支持。

计费说明

目前,长期记忆项目本身的服务计算资源当前免费,项目费用仅包含:

  1. 底层资源费:RDS for PostgreSQL 实例费用。

  2. 模型调用费:内置 LLM 和 Embedding 模型的 API 按量调用费用。

其正式收费时间将另行公告。

快速体验

步骤一:创建长期记忆

  1. 登录RDS控制台,单击左侧导航栏中的长期记忆

  2. 在实例列表页面,单击创建项目

  3. 根据页面提示,选择长期记忆类型并完成后续配置。image

  4. 购买成功后,请返回控制台并等待实例状态变为运行中

步骤二:获取连接地址与API Key

获取连接地址:在长期记忆列表页面,单击目标实例的项目ID进入详情页,在基本信息页签中查看外网连接地址

说明

访问地址:通过Mem0 SDK或者官网 API调用地址实现长期记忆管理。

Mem0 SDK Host:http://<外网访问地址>/memory/。

示例:http://<外网访问地址>/memory/v1/memories/。

获取API Key:在长期记忆列表页面,单击目标实例的项目ID进入详情页,在基本信息页签中右上角,点击获取API Key获取ServiceKey

image

步骤三:网络配置

为保证服务能够被正常调用,需要进行如下网络配置。

允许实例访问公网

  1. 点击进入实例详情的基本信息页。

  2. 打开网络信息 > 允许实例访问公网按钮。

配置白名单

  1. 在实例详情页的基本信息区域,找到白名单信息

  2. 单击添加白名单分组,将您的客户端或测试服务器的IP地址添加到白名单中。

步骤四:接入RDS长期记忆SDK示例

安装官方SDK

pip3 install mem0ai

配置环境变量

export MEM0_HOST="http://<your-host>:80/memory"  # 服务地址
export MEM0_API_KEY="<your-api-key>"             # API 密钥

调用SDK完整示例代码

仅向量存储(不含graph)
Python示例代码
#!/usr/bin/env python3
"""
Mem0 SDK 基本功能测试脚本
使用 MemoryClient 进行增删改查操作

使用方法:
    python test_mem0_sdk_basic.py
"""
import os
import json
import time
from mem0 import MemoryClient

# ============================================

def main():
    # 从环境变量获取配置
    api_key = os.environ.get("MEM0_API_KEY")
    host = os.environ.get("MEM0_HOST")

    print("=" * 60)
    print("Mem0 SDK 基本功能测试")
    print("=" * 60)
    print(f"服务地址: {host}")

    # 初始化客户端
    client = MemoryClient(host=host, api_key=api_key)

    # 测试用户
    user_id = f"sdk_test_user_{int(time.time())}"
    print(f"测试用户: {user_id}")
    print("=" * 60)

    memory_id = None

    try:
        # =================== 1. 添加记忆 (Add) ===================
        print("\n[1] 添加记忆 (Add)")
        print("-" * 40)

        messages = [
            {"role": "user", "content": "我是张三,在北京工作,喜欢打篮球。"},
            {"role": "assistant", "content": "你好张三!北京是个好地方,篮球也是很棒的运动。"},
        ]

        result = client.add(messages, user_id=user_id)
        print(f"添加结果: {json.dumps(result, ensure_ascii=False, indent=2)}")

        # 等待处理完成
        time.sleep(2)

        # =================== 2. 获取所有记忆 (Get All) ===================
        print("\n[2] 获取所有记忆 (Get All)")
        print("-" * 40)

        all_memories = client.get_all(user_id=user_id)
        print(f"记忆列表: {json.dumps(all_memories, ensure_ascii=False, indent=2)}")

        memories = all_memories.get("results", [])
        print(f"共 {len(memories)} 条记忆")

        if memories:
            memory_id = memories[0]["id"]
            print(f"第一条记忆 ID: {memory_id}")

        # =================== 3. 搜索记忆 (Search) ===================
        print("\n[3] 搜索记忆 (Search)")
        print("-" * 40)

        search_result = client.search("张三在哪里工作", user_id=user_id)
        print(f"搜索结果: {json.dumps(search_result, ensure_ascii=False, indent=2)}")

        # =================== 4. 获取单条记忆 (Get) ===================
        print("\n[4] 获取单条记忆 (Get)")
        print("-" * 40)

        if memory_id:
            single_memory = client.get(memory_id)
            print(f"记忆详情: {json.dumps(single_memory, ensure_ascii=False, indent=2)}")
        else:
            print("无可用记忆 ID")

        # =================== 5. 更新记忆 (Update) ===================
        print("\n[5] 更新记忆 (Update)")
        print("-" * 40)

        if memory_id:
            new_content = "张三现在在上海工作,依然喜欢打篮球"
            update_result = client.update(memory_id, new_content)
            print(f"更新结果: {json.dumps(update_result, ensure_ascii=False, indent=2)}")
        else:
            print("无可用记忆 ID")

        # =================== 6. 获取记忆历史 (History) ===================
        print("\n[6] 获取记忆历史 (History)")
        print("-" * 40)

        if memory_id:
            history = client.history(memory_id)
            print(f"历史记录: {json.dumps(history, ensure_ascii=False, indent=2)}")
        else:
            print("无可用记忆 ID")

        # =================== 7. 删除单条记忆 (Delete) ===================
        print("\n[7] 删除单条记忆 (Delete)")
        print("-" * 40)

        if memory_id:
            delete_result = client.delete(memory_id)
            print(f"删除结果: {json.dumps(delete_result, ensure_ascii=False, indent=2)}")
        else:
            print("无可用记忆 ID")

        # =================== 8. 验证删除 ===================
        print("\n[8] 验证删除")
        print("-" * 40)

        final_memories = client.get_all(user_id=user_id)
        remaining = len(final_memories.get("results", []))
        print(f"剩余记忆数: {remaining}")

        # =================== 9. 删除所有记忆 (Delete All) ===================
        print("\n[9] 删除所有记忆 (Delete All)")
        print("-" * 40)

        delete_all_result = client.delete_all(user_id=user_id)
        print(f"删除全部结果: {json.dumps(delete_all_result, ensure_ascii=False, indent=2)}")

        # =================== 测试完成 ===================
        print("\n" + "=" * 60)
        print("测试完成!")
        print("=" * 60)

    except Exception as e:
        print(f"\n错误: {e}")
        import traceback
        traceback.print_exc()
        return 1

    return 0

if __name__ == "__main__":
    exit(main())

向量 + 图混合存储(包含graph)

Python示例代码

#!/usr/bin/env python3
"""
Mem0 SDK 图搜索功能测试脚本
使用 MemoryClient 进行带图搜索的增删改查操作

功能特点:
- 启用 enable_graph=True 进行图搜索
- 展示 relations(图关系)结果
- 对比普通搜索和图搜索的差异

使用方法:
    python 当前文件
"""

import os
import json
import time
from mem0 import MemoryClient

# ============================================
# 配置
# ============================================
HOST = "http://<your-host>:80/memory"  # 服务地址
API_KEY = "<your-api-key>"              # API 密钥

# ============================================


def print_json(data, title=None):
    """格式化打印 JSON 数据"""
    if title:
        print(f"\n{title}:")
    print(json.dumps(data, ensure_ascii=False, indent=2))


def print_relations(relations):
    """格式化打印图关系"""
    if not relations:
        print("  (无图关系)")
        return
    
    print(f"  共 {len(relations)} 条关系:")
    for i, rel in enumerate(relations, 1):
        source = rel.get("source", "?")
        relationship = rel.get("relationship", "?")
        destination = rel.get("destination") or rel.get("target", "?")
        print(f"    [{i}] {source} --[{relationship}]--> {destination}")


def main():
    # 从环境变量获取配置
    api_key = os.environ.get("MEM0_API_KEY", API_KEY)
    host = os.environ.get("MEM0_HOST", HOST)
    
    print("=" * 70)
    print("Mem0 SDK 图搜索功能测试")
    print("=" * 70)
    print(f"服务地址: {host}")
    
    # 初始化客户端
    client = MemoryClient(host=host, api_key=api_key)
    
    # 测试用户
    user_id = "user_001"
    print(f"测试用户: {user_id}")
    print("=" * 70)
    
    try:
        # =================== 1. 添加多条记忆(构建图关系) ===================
        print("\n[1] 添加多条记忆(构建图关系)")
        print("-" * 50)
        
        # 第一轮对话:个人信息
        messages1 = [
            {"role": "user", "content": "我是张三,在阿里巴巴工作,负责AI平台研发。"},
            {"role": "assistant", "content": "你好张三!阿里巴巴的AI平台是很有影响力的。"},
        ]
        result1 = client.add(messages1, user_id=user_id)
        print(f"添加结果1: {json.dumps(result1, ensure_ascii=False)[:200]}...")
        
        time.sleep(2)
        
        # 第二轮对话:兴趣爱好
        messages2 = [
            {"role": "user", "content": "我喜欢打篮球,周末经常和李四一起打球。"},
            {"role": "assistant", "content": "篮球是很棒的运动,和朋友一起更有趣!"},
        ]
        result2 = client.add(messages2, user_id=user_id)
        print(f"添加结果2: {json.dumps(result2, ensure_ascii=False)[:200]}...")
        
        time.sleep(2)
        
        # 第三轮对话:更多关系
        messages3 = [
            {"role": "user", "content": "我的老板是王总,他是数据智能部门的负责人。"},
            {"role": "assistant", "content": "了解,王总是数据智能部门的领导。"},
        ]
        result3 = client.add(messages3, user_id=user_id)
        print(f"添加结果3: {json.dumps(result3, ensure_ascii=False)[:200]}...")
        
        # 等待图构建完成
        print("\n等待图关系构建完成...")
        time.sleep(5)
        
        # =================== 2. 获取所有记忆(带图) ===================
        print("\n[2] 获取所有记忆(enable_graph=True)")
        print("-" * 50)
        
        all_memories = client.get_all(user_id=user_id, enable_graph=True)
        
        results = all_memories.get("results", [])
        relations = all_memories.get("relations", [])
        
        print(f"\n向量搜索结果: 共 {len(results)} 条记忆")
        for i, mem in enumerate(results[:5], 1):
            print(f"  [{i}] {mem.get('memory', '')[:50]}...")
        
        print(f"\n图关系结果:")
        print_relations(relations)
        
        # =================== 3. 图搜索 vs 普通搜索 ===================
        print("\n[3] 图搜索 vs 普通搜索 对比")
        print("-" * 50)
        
        query = "张三在哪里工作?"
        print(f"搜索查询: {query}")
        
        # 3.1 普通搜索(不启用图)
        print("\n【普通搜索】enable_graph=False:")
        search_normal = client.search(query, user_id=user_id, enable_graph=False)
        normal_results = search_normal.get("results", [])
        normal_relations = search_normal.get("relations")
        
        print(f"  向量结果数: {len(normal_results)}")
        for i, mem in enumerate(normal_results[:3], 1):
            score = mem.get("score", "N/A")
            memory = mem.get("memory", "")[:40]
            print(f"    [{i}] score={score:.4f} | {memory}...")
        print(f"  图关系: {normal_relations}")
        
        # 3.2 图搜索(启用图)
        print("\n【图搜索】enable_graph=True:")
        search_graph = client.search(query, user_id=user_id, enable_graph=True)
        graph_results = search_graph.get("results", [])
        graph_relations = search_graph.get("relations", [])
        
        print(f"  向量结果数: {len(graph_results)}")
        for i, mem in enumerate(graph_results[:3], 1):
            score = mem.get("score", "N/A")
            memory = mem.get("memory", "")[:40]
            print(f"    [{i}] score={score:.4f} | {memory}...")
        
        print(f"  图关系结果:")
        print_relations(graph_relations)
        
        # =================== 4. 多关键词图搜索 ===================
        print("\n[4] 多关键词图搜索")
        print("-" * 50)
        
        queries = [
            "张三和李四的关系",
            "谁是王总",
            "篮球相关的活动",
        ]
        
        for query in queries:
            print(f"\n查询: {query}")
            result = client.search(query, user_id=user_id, enable_graph=True)
            
            results = result.get("results", [])
            relations = result.get("relations", [])
            
            print(f"  向量结果数: {len(results)}")
            if results:
                print(f"    Top1: {results[0].get('memory', '')[:50]}...")
            
            print(f"  图关系:")
            print_relations(relations)
        
        # =================== 5. 清理测试数据 ===================
        print("\n[5] 清理测试数据")
        print("-" * 50)
        
        delete_result = client.delete_all(user_id=user_id)
        print(f"删除结果: {json.dumps(delete_result, ensure_ascii=False)}")
        
        # =================== 测试完成 ===================
        print("\n" + "=" * 70)
        print("图搜索测试完成!")
        print("=" * 70)
        
        print("\n【总结】")
        print("- enable_graph=False: 仅返回向量搜索结果 (results)")
        print("- enable_graph=True:  返回向量结果 (results) + 图关系 (relations)")
        print("- 图关系格式: source --[relationship]--> destination")
        
    except Exception as e:
        print(f"\n错误: {e}")
        import traceback
        traceback.print_exc()
        
        # 清理测试数据
        try:
            client.delete_all(user_id=user_id)
            print("已清理测试数据")
        except Exception:
            pass
        
        return 1
    
    return 0


if __name__ == "__main__":
    exit(main())

附录:API 参考

API目录

操作

方法

端点

获取全部

POST

/v2/memories/

搜索

POST

/v2/memories/search/

添加

POST

/v1/memories/

获取单条

GET

/v1/memories/{id}/

更新

PUT

/v1/memories/{id}/

删除单条

DELETE

/v1/memories/{id}/

删除全部

DELETE

/v1/memories/

请求头

所有API请求都需要在HTTP Header中包含Authorization: Token <your-api-key>进行认证。

请求示例

此处仅列举部分API参考。

添加记忆(Create Memories)

存储新的记忆。服务会自动对messages内容进行分析,生成会话摘要和语义记忆。

curl -X POST "http://<host>/memory/v1/memories/" \
  -H "Authorization: Token <api-key>" \
  -H "Content-Type: application/json" \
  -d '{
    "messages": [
      {"role": "user", "content": "我叫张三,在阿里巴巴工作"}
    ],
    "user_id": "user_001",
    "agent_id": "my_agent",
    "enable_graph": false
  }'

搜索记忆(Search Memories)

根据查询字符串,搜索最相关的记忆。

curl -X POST "http://<host>/memory/v2/memories/search/" \
  -H "Authorization: Token <api-key>" \
  -H "Content-Type: application/json" \
  -d '{"query": "搜索内容", "user_id": "user_001"}'

获取全部记忆(Get Memories)

获取指定范围内的所有原始记忆。

curl -X POST "http://<host>/memory/v2/memories/" \
  -H "Authorization: Token <api-key>" \
  -H "Content-Type: application/json" \
  -d '{"user_id": "user_001"}'

删除单条记忆(Delete Memories)

根据记忆ID删除一条指定的记忆。

curl -X DELETE "http://<host>/memory/v1/memories/<memory-id>/" \
  -H "Authorization: Token <api-key>"

获取单条记忆

curl -X GET "http://<host>/memory/v1/memories/<Memory_Id>/" \
 -H "Authorization: Token <api-key>"

图搜索(enable_graph=true)

curl -X POST "http://<host>/memory/v2/memories/search/" \
  -H "Content-Type: application/json" \
  -H "Authorization: Token <api-key>" \
  -d '{
    "query": "张三的工作",
    "user_id": "user_001",
    "enable_graph": true,
    "limit": 10
  }'

普通搜索(enable_graph=false 或不传)

curl -X POST "http://<host>/memory/v2/memories/search/" \
  -H "Content-Type: application/json" \
  -H "Authorization: Token <api-key>" \
  -d '{
    "query": "张三在哪里工作",
    "user_id": "user_001",
    "enable_graph": false,
    "limit": 10
  }'

获取所有记忆(带图)

curl -X POST "http://<host>/memory/v2/memories/" \
  -H "Content-Type: application/json" \
  -H "Authorization: Token <api-key>" \
  -d '{
    "user_id": "user_001",
    "enable_graph": true
  }'