编程 Cognee 深度实战:当 AI Agent 装上持久化记忆——从向量搜索到知识图谱的生产级完全指南(2026)

2026-06-09 23:18:18 +0800 CST views 10

Cognee 深度实战:当 AI Agent 装上持久化记忆——从向量搜索到知识图谱的生产级完全指南(2026)

摘要:AI Agent 的记忆问题一直是制约其智能化的核心瓶颈。本文深入解析开源项目 Cognee 如何通过向量搜索与知识图谱的融合,为 AI Agent 提供持久化、动态化的记忆能力。从核心概念、架构设计到生产级代码实战,带你掌握下一代 AI 记忆系统的完全指南。


目录

  1. 背景介绍:AI Agent 的记忆困境
  2. 核心概念:从向量搜索到知识图谱
  3. Cognee 架构深度分析
  4. 代码实战:从安装到生产部署
  5. 性能优化:让记忆系统快如闪电
  6. 总结与展望:AI 记忆的未来

1. 背景介绍:AI Agent 的记忆困境

1.1 为什么 AI Agent 需要持久化记忆?

在 2026 年的今天,AI Agent 已经渗透到编程、运维、客服、科研等各个领域。然而,一个核心问题始终困扰着开发者和研究者:AI Agent 如何"记住"过去的信息?

传统的 LLM(大语言模型)受限于上下文窗口(Context Window),即使 GPT-4o、Claude 3.7 已经支持 128K 甚至 1M tokens 的上下文,但实际应用中仍面临三大困境:

困境问题描述影响
上下文污染历史对话占据大量 token,导致有效信息密度下降推理质量降低、成本飙升
遗忘问题会话结束后,所有信息丢失,无法跨会话记忆用户体验差、无法积累知识
知识孤岛每个 Agent 实例独立运行,无法共享记忆团队协作困难、重复计算

典型场景

# 场景1:客服 Agent 的遗忘问题
user: "我上次反映的订单问题解决了吗?"
agent: "抱歉,我没有你的历史记录,请重新描述问题。"

# 场景2:编程 Agent 的上下文污染
# 当对话历史超过 50 轮,有效信息被淹没在海量 token 中
# 每次推理都需要处理 30K+ tokens,成本高、速度慢

# 场景3:多 Agent 协作的知识孤岛
agent_a: "我刚刚分析了用户需求,结论是..."
agent_b: "我不知道 agent_a 分析了什么,请重新告诉我。"

1.2 现有方案的局限性

目前业界主要有以下几种记忆方案,但各有明显短板:

方案1:纯向量数据库(Vector DB)

代表工具:Pinecone、Weaviate、Qdrant、Chroma

工作原理

# 将历史信息向量化后存储
from langchain.vectorstores import Chroma
from langchain.embeddings import OpenAIEmbeddings

embeddings = OpenAIEmbeddings()
vectorstore = Chroma(embedding_function=embeddings)

# 存储记忆
vectorstore.add_documents([
    "用户喜欢用 Python 而不是 JavaScript",
    "项目使用 FastAPI + PostgreSQL 架构",
    "上次讨论的 bug 是数据库连接池泄漏"
])

# 检索记忆
memory = vectorstore.similarity_search("技术栈选择", k=3)

局限性

  • 缺乏关系建模:向量搜索只能找到"语义相似"的内容,无法建模"用户A是用户B的上级"这类关系
  • 上下文丢失:每次检索是独立的,无法构建连贯的"记忆链"
  • 精确度低:向量相似度不等于语义相关性,容易召回无关信息

方案2:纯图数据库(Graph DB)

代表工具:Neo4j、Nebula Graph、TigerGraph

工作原理

// 构建知识图谱
CREATE (u:User {name: "张三"})
CREATE (p:Project {name: "AI记忆系统"})
CREATE (t:Tech {name: "Python"})
CREATE (u)-[:WORKS_ON]->(p)
CREATE (p)-[:USES]->(t)
CREATE (u)-[:PREFERS]->(t)

// 查询记忆
MATCH (u:User)-[:WORKS_ON]->(p:Project)-[:USES]->(t:Tech)
RETURN u.name, p.name, collect(t.name)

局限性

  • 语义理解弱:图数据库依赖精确的结构化查询,无法处理"帮我找类似的项目"这类语义查询
  • 构建成本高:需要手动定义 schema、抽取实体关系,维护成本极高
  • 非结构化数据支持差:对于文本、代码、日志等非结构化数据,图数据库无法直接处理

方案3:RAG(检索增强生成)

工作原理

# RAG 流程
query = "用户上次反馈的问题是什么?"

# 1. 向量检索
retrieved_docs = vectorstore.similarity_search(query, k=5)

# 2. 拼接上下文
context = "\n".join([doc.page_content for doc in retrieved_docs])

# 3. 生成回答
prompt = f"基于以下上下文:\n{context}\n\n回答问题:{query}"
answer = llm(prompt)

局限性

  • 检索质量不稳定:依赖向量搜索的质量,容易检索到无关信息
  • 缺乏记忆更新机制:RAG 是静态的,无法动态更新记忆
  • 多轮对话支持差:无法有效管理多轮对话中的记忆演进

1.3 Cognee 的破局之道

Cognee(GitHub: topoteretes/cognee)是一个开源工具/平台,它将向量搜索图数据库深度融合,为 AI Agent 提供:

持久化记忆:跨会话、跨实例的记忆存储
动态知识图谱:自动从非结构化数据中提取实体关系
多模态支持:文本、代码、图像、音频统一处理
语义+关系双重检索:既能量化语义相似度,又能建模复杂关系
低代码集成:与 LangChain、LlamaIndex、AutoGen 等框架无缝集成

核心设计哲学

"Memory should be a first-class citizen in AI systems, not an afterthought."
(记忆应该是 AI 系统的头等公民,而不是事后补丁。)


2. 核心概念:从向量搜索到知识图谱

2.1.1 什么是向量搜索?

向量搜索是将非结构化数据(文本、图像、音频)转换为高维向量(embeddings),然后通过计算向量之间的距离(通常是余弦相似度或欧氏距离)来找到"最相似"的内容。

数学原理

给定查询向量 $q$ 和文档向量 $d$,余弦相似度定义为:

$$
\text{cosine_similarity}(q, d) = \frac{q \cdot d}{|q| |d|} = \frac{\sum_{i=1}^{n} q_i d_i}{\sqrt{\sum_{i=1}^{n} q_i^2} \sqrt{\sum_{i=1}^{n} d_i^2}}
$$

代码示例

import numpy as np
from openai import OpenAI

client = OpenAI()

# 1. 将文本转换为向量
def get_embedding(text):
    response = client.embeddings.create(
        model="text-embedding-3-small",
        input=text
    )
    return response.data[0].embedding

# 2. 计算余弦相似度
def cosine_similarity(v1, v2):
    v1 = np.array(v1)
    v2 = np.array(v2)
    return np.dot(v1, v2) / (np.linalg.norm(v1) * np.linalg.norm(v2))

# 3. 示例
query = "如何优化 Python 代码性能?"
doc1 = "Python 性能优化技巧:使用 NumPy 向量化操作"
doc2 = "JavaScript 异步编程最佳实践"

q_emb = get_embedding(query)
d1_emb = get_embedding(doc1)
d2_emb = get_embedding(doc2)

print(f"Query vs Doc1: {cosine_similarity(q_emb, d1_emb):.4f}")  # 高相似度 ~0.85
print(f"Query vs Doc2: {cosine_similarity(q_emb, d2_emb):.4f}")  # 低相似度 ~0.45

2.1.2 向量搜索的痛点

尽管向量搜索强大,但在 AI Agent 记忆场景中存在明显短板:

痛点1:缺乏精确关系建模

# 向量搜索无法区分以下两句的细微差别
sentence1 = "Alice 是 Bob 的经理"
sentence2 = "Bob 是 Alice 的经理"

# 它们的向量表示可能非常相似(余弦相似度 > 0.9)
# 但语义关系完全相反!

痛点2:上下文丢失

# 记忆1:"用户喜欢用 Python"
# 记忆2:"用户最近在学 Rust"

# 向量搜索会独立检索这两条记忆
# 但无法推理出:"用户可能会问 Python 和 Rust 的对比"

痛点3:长尾知识难以检索

向量搜索对于"显而易见"的相似内容效果很好,但对于隐含的、间接相关的知识,检索效果差。

2.2 知识图谱(Knowledge Graph)深度解析

2.2.1 什么是知识图谱?

知识图谱是一种结构化知识表示,用实体(Entity)、关系(Relation)、属性(Attribute)三元组来存储知识:

(实体1) --[关系]--> (实体2)
(Alice) --[WORKS_FOR]--> (Acme Corp)
(Alice) --[HAS_SKILL]--> (Python)
(ProjectX) --[USES_TECH]--> (PostgreSQL)

核心优势

  • 精确关系建模:能准确表示"谁是谁的上级"
  • 推理能力强:通过图遍历可以发现隐含知识(如"Alice 的同事是谁")
  • 可解释性好:推理路径清晰(A→B→C,所以 A 和 C 有关系)

2.2.2 知识图谱的构建流程

构建知识图谱通常包含以下步骤:

# 步骤1:实体抽取(Named Entity Recognition)
text = "张三在阿里巴巴工作,他负责 Python 后端开发。"
entities = extract_entities(text)
# 输出:["张三"(PERSON), "阿里巴巴"(ORG), "Python"(TECH)]

# 步骤2:关系抽取(Relation Extraction)
relations = extract_relations(text, entities)
# 输出:[(张三, WORKS_FOR, 阿里巴巴), (张三, USES, Python)]

# 步骤3:实体链接(Entity Linking)
# 将抽取的实体链接到知识库中的标准实体
# 如:"阿里巴巴" → 知识库中的 "Alibaba Group"

# 步骤4:图谱存储
from neo4j import GraphDatabase

driver = GraphDatabase.driver("bolt://localhost:7687")
with driver.session() as session:
    session.run(
        "CREATE (p:Person {name: $name})-[r:WORKS_FOR]->(o:Org {name: $org})",
        name="张三", org="阿里巴巴"
    )

痛点

  • 构建成本高:需要 NLP 模型进行实体/关系抽取
  • schema 设计复杂:需要预先定义实体类型和关系类型
  • 非结构化数据处理能力弱:对于自由文本、代码等,难以直接建模

2.3 Cognee 的融合方案:向量 + 图

Cognee 的核心创新在于:用向量搜索处理非结构化数据,用知识图谱建模结构化关系,两者互为索引、互相增强

2.3.1 架构设计

┌─────────────────────────────────────────────────────┐
│                   Cognee Memory                    │
├─────────────────────────────────────────────────────┤
│                                                     │
│  ┌──────────────┐         ┌──────────────┐       │
│  │ Vector Store  │ ←─────→ │  Graph Store  │       │
│  │  (向量索引)    │  互为索引   │  (关系索引)    │       │
│  └──────────────┘         └──────────────┘       │
│         ↓                        ↓                 │
│  "语义相似的内容"          "相关的实体关系"         │
│                                                     │
└─────────────────────────────────────────────────────┘

关键机制

  1. 向量 → 图:向量检索的结果,作为图遍历的起点

    # 先向量检索到相关节点
    similar_nodes = vector_search("Python 性能优化")
    # 再从这些节点出发,遍历图关系
    related_nodes = graph.traverse(similar_nodes, depth=2)
    
  2. 图 → 向量:图遍历发现的实体,用向量搜索找到相似内容

    # 先图遍历找到相关实体
    alice_projects = graph.query("MATCH (u:User)-[:WORKS_ON]->(p:Project) WHERE u.name='Alice' RETURN p")
    # 再用这些项目的描述做向量搜索,找到类似项目
    similar_projects = vector_search([p.description for p in alice_projects])
    
  3. 统一召回:向量和图的检索结果融合排序后返回

    results = merge_and_rerank(
        vector_results=vector_search(query),
        graph_results=graph_search(query),
        weights=[0.6, 0.4]  # 向量权重0.6,图权重0.4
    )
    

2.3.2 数据模型

Cognee 中的数据单元是 Memory Block(记忆块),每个记忆块同时包含:

class MemoryBlock:
    id: str                 # 唯一标识
    content: str             # 原始内容(文本/代码/图像URL)
    embedding: List[float]   # 向量表示(768维/1536维)
    metadata: Dict           # 元数据(时间戳、来源、作者等)
    relations: List[Tuple]   # 关联关系(指向其他 MemoryBlock)
    block_type: str          # 类型(text/code/image/conversation)

存储示例

{
  "id": "mem_001",
  "content": "用户反馈:登录页面加载慢,耗时超过5秒",
  "embedding": [0.023, -0.145, ..., 0.782],  // 768维
  "metadata": {
    "timestamp": "2026-06-09T15:30:00Z",
    "source": "user_feedback",
    "priority": "high"
  },
  "relations": [
    ("mem_001", "RELATED_TO", "mem_042"),  // 关联到技术方案
    ("mem_001", "REPORTED_BY", "user_123")
  ],
  "block_type": "text"
}

3. Cognee 架构深度分析

3.1 整体架构

Cognee 采用分层架构,从下到上分为:

┌─────────────────────────────────────────────────┐
│            Application Layer                    │
│  (LangChain / LlamaIndex / AutoGen 集成)       │
└─────────────────────────────────────────────────┘
                     ↓
┌─────────────────────────────────────────────────┐
│              Cognee Core                       │
│  ┌──────────┐ ┌──────────┐ ┌──────────┐      │
│  │  Memory   │ │  Search  │ │  Graph   │      │
│  │  Manager  │ │  Engine  │ │  Builder │      │
│  └──────────┘ └──────────┘ └──────────┘      │
└─────────────────────────────────────────────────┘
                     ↓
┌─────────────────────────────────────────────────┐
│            Storage Layer                       │
│  ┌──────────────┐    ┌──────────────┐        │
│  │ Vector DB     │    │ Graph DB      │        │
│  │ (Qdrant/     │    │ (Neo4j/      │        │
│  │  Weaviate)   │    │  NetworkX)   │        │
│  └──────────────┘    └──────────────┘        │
└─────────────────────────────────────────────────┘

3.2 核心模块详解

3.2.1 Memory Manager(记忆管理器)

职责

  • 记忆的 CRUD(创建、读取、更新、删除)
  • 记忆的分块与向量化
  • 记忆的版本控制(类似 Git)

关键代码

from cognee import MemoryManager

mm = MemoryManager()

# 1. 创建记忆
mm.add(
    content="用户希望增加深色模式支持",
    metadata={"source": "user_feedback", "priority": "medium"},
    block_type="text"
)
# 返回:MemoryBlock(id="mem_789", ...)

# 2. 批量创建记忆
mm.add_batch([
    {"content": "技术栈:Python + FastAPI", "metadata": {"category": "tech"}},
    {"content": "部署环境:Docker + K8s", "metadata": {"category": "devops"}},
])

# 3. 更新记忆
mm.update(
    memory_id="mem_789",
    content="用户强烈要求增加深色模式,影响用户体验评分",
    metadata={"priority": "high", "updated_at": "2026-06-09"}
)

# 4. 删除记忆(软删除,保留历史版本)
mm.delete(memory_id="mem_789", soft_delete=True)

记忆分块策略

Cognee 支持多种分块策略,以适应不同类型的内容:

from cognee.chunking import SemanticChunker, FixedSizeChunker

# 策略1:固定大小分块(适合代码)
chunker1 = FixedSizeChunker(chunk_size=512, overlap=50)
chunks1 = chunker1.chunk("""def add(a, b):
    return a + b

def subtract(a, b):
    return a - b
""")
# 输出:[chunk1, chunk2, ...] 每个 chunk 最多 512 字符,相邻 chunk 重叠 50 字符

# 策略2:语义分块(适合长文本)
chunker2 = SemanticChunker(threshold=0.7)  # 语义相似度低于 0.7 时切分
text = """
第一部分:项目背景
这是一个 AI 记忆系统项目。

第二部分:技术选型
我们使用 Python + FastAPI。
"""
chunks2 = chunker2.chunk(text)
# 输出:[chunk_part1, chunk_part2] 按语义边界自动切分

3.2.2 Search Engine(搜索引擎)

职责

  • 向量搜索(语义检索)
  • 图搜索(关系检索)
  • 混合搜索(向量+图融合)

关键代码

from cognee import SearchEngine

se = SearchEngine()

# 1. 纯向量搜索
vector_results = se.vector_search(
    query="如何优化 API 响应时间?",
    top_k=10,
    filters={"metadata.source": "tech_discussion"}  # 可选过滤条件
)
# 返回:
# [
#   {"memory_id": "mem_123", "content": "...", "score": 0.89},
#   {"memory_id": "mem_456", "content": "...", "score": 0.85},
#   ...
# ]

# 2. 纯图搜索
graph_results = se.graph_search(
    query="MATCH (u:User)-[:REPORTED]->(i:Issue) WHERE u.name='Alice' RETURN i",
    graph_db="neo4j"
)
# 返回:Alice 报告的所有 Issue

# 3. 混合搜索(推荐)
hybrid_results = se.hybrid_search(
    query="Python 性能优化技巧",
    vector_weight=0.6,  # 向量搜索权重
    graph_weight=0.4,    # 图搜索权重
    top_k=10
)
# 返回:融合排序后的结果

混合搜索的融合算法

Cognee 使用 RRF(Reciprocal Rank Fusion) 算法融合向量和图的搜索结果:

def reciprocal_rank_fusion(vector_results, graph_results, k=60):
    """
    RRF 融合算法
    score = Σ (1 / (k + rank_i))
    """
    scores = {}
    
    # 向量搜索结果的排名
    for rank, item in enumerate(vector_results, start=1):
        doc_id = item["memory_id"]
        scores[doc_id] = scores.get(doc_id, 0) + 1 / (k + rank)
    
    # 图搜索结果的排名
    for rank, item in enumerate(graph_results, start=1):
        doc_id = item["memory_id"]
        scores[doc_id] = scores.get(doc_id, 0) + 1 / (k + rank)
    
    # 按融合分数排序
    fused_results = sorted(scores.items(), key=lambda x: x[1], reverse=True)
    return fused_results

3.2.3 Graph Builder(图谱构建器)

职责

  • 从非结构化数据中提取实体和关系
  • 构建/更新知识图谱
  • 实体链接与消歧

关键代码

from cognee import GraphBuilder

gb = GraphBuilder()

# 1. 从文本自动构建图谱
text = """
张三在阿里巴巴工作,他负责 Python 后端开发。
李四在腾讯工作,他擅长 Java 和分布式系统。
张三和李四曾是大学同学。
"""

gb.build_from_text(
    text=text,
    entity_types=["PERSON", "ORG", "TECH"],  # 关注的实体类型
    relation_types=["WORKS_FOR", "HAS_SKILL", "CLASSMATE"]  # 关注的关系类型
)
# 自动抽取:
# (张三, WORKS_FOR, 阿里巴巴)
# (张三, HAS_SKILL, Python)
# (李四, WORKS_FOR, 腾讯)
# (李四, HAS_SKILL, Java)
# (张三, CLASSMATE, 李四)

# 2. 从代码构建图谱(代码理解场景)
code = """
class UserService:
    def __init__(self, db: Database):
        self.db = db
    
    def get_user(self, user_id: int):
        return self.db.query(User).filter_by(id=user_id).first()
"""

gb.build_from_code(
    code=code,
    language="python",
    extract=["class", "method", "dependency"]  # 抽取类、方法、依赖关系
)
# 自动构建:
# (UserService, HAS_METHOD, get_user)
# (UserService, DEPENDS_ON, Database)

# 3. 手动添加关系
gb.add_relation(
    subject="mem_001",
    predicate="RELATED_TO",
    object="mem_042",
    confidence=0.95  # 置信度
)

实体链接(Entity Linking)

当同一个实体有多种表达方式时(如"阿里巴巴"、"阿里"、"Alibaba"、"Alibaba Group"),需要链接到同一个标准实体:

# 实体链接配置
gb.configure_entity_linking(
    method="embedding_similarity",  # 基于向量相似度
    threshold=0.85,                 # 相似度阈值
    knowledge_base="dbpedia"        # 参考知识库(可选)
)

# 自动链接示例
# "阿里巴巴" → 标准实体 "Alibaba_Group"
# "阿里" → 标准实体 "Alibaba_Group"
# "Alibaba" → 标准实体 "Alibaba_Group"

3.3 存储层详解

Cognee 的存储层支持多种后端,用户可以根据需求灵活选择:

3.3.1 向量数据库支持

向量数据库优点缺点适用场景
Qdrant速度快、支持过滤、云原生生态较新生产环境、大规模向量搜索
Weaviate功能全面、支持多模态配置复杂多模态场景(文本+图像)
Chroma轻量级、易上手规模受限本地开发、小规模应用
Pinecone托管服务、无需运维收费、数据在外网快速原型、无运维团队

配置示例(Qdrant)

from cognee.storage import QdrantVectorStore

vector_store = QdrantVectorStore(
    host="localhost",
    port=6333,
    collection_name="cognee_memories",
    embedding_dim=768,  # 向量维度(取决于 embedding 模型)
    distance_metric="Cosine"  # 距离度量:Cosine / Euclidean / Dot
)

# 初始化(创建 collection)
vector_store.initialize()

# 插入向量
vector_store.upsert(
    ids=["mem_001", "mem_002"],
    vectors=[[-0.023, 0.145, ..., -0.782], [...]],
    payloads=[  # 附加信息(不参加向量计算,但可过滤)
        {"content": "用户反馈:登录慢", "timestamp": "2026-06-09"},
        {"content": "技术方案:CDN加速", "timestamp": "2026-06-09"}
    ]
)

# 向量搜索
results = vector_store.search(
    query_vector=[0.023, -0.145, ..., 0.782],
    top_k=10,
    filters={"timestamp": {"$gte": "2026-06-01"}}  # 可选过滤
)

3.3.2 图数据库支持

图数据库优点缺点适用场景
Neo4j成熟稳定、Cypher 易用单机性能瓶颈生产环境、复杂关系查询
Nebula Graph分布式、高性能学习曲线陡超大规模图谱(亿级边)
NetworkX轻量级、纯 Python不支持持久化本地开发、小规模图谱
TigerGraph实时图分析闭源、收费企业级实时推荐系统

配置示例(Neo4j)

from cognee.storage import Neo4jGraphStore

graph_store = Neo4jGraphStore(
    uri="bolt://localhost:7687",
    username="neo4j",
    password="password",
    database="cognee"
)

# 初始化(创建索引)
graph_store.initialize()

# 插入节点和关系
graph_store.add_node(
    node_id="user_001",
    labels=["User"],
    properties={"name": "Alice", "email": "alice@example.com"}
)

graph_store.add_edge(
    source_id="user_001",
    target_id="project_001",
    edge_type="WORKS_ON",
    properties={"since": "2026-01-01"}
)

# 图查询(Cypher)
results = graph_store.query("""
    MATCH (u:User)-[:WORKS_ON]->(p:Project)
    WHERE u.name = $name
    RETURN u.name, p.name, p.status
""", parameters={"name": "Alice"})

# 图遍历(找邻居)
neighbors = graph_store.traverse(
    start_node="user_001",
    edge_types=["WORKS_ON", "FRIEND_OF"],
    max_depth=2,
    direction="outgoing"
)

4. 代码实战:从安装到生产部署

4.1 安装与配置

4.1.1 基础安装

# 方式1: pip 安装(推荐)
pip install cognee

# 方式2:从源码安装(最新功能)
git clone https://github.com/topoteretes/cognee.git
cd cognee
pip install -e .

4.1.2 依赖服务启动

Cognee 需要向量数据库和图数据库,推荐使用 Docker Compose 一键启动:

# docker-compose.yml
version: '3.8'

services:
  qdrant:
    image: qdrant/qdrant:latest
    ports:
      - "6333:6333"
    volumes:
      - qdrant_data:/qdrant/storage

  neo4j:
    image: neo4j:5.0
    ports:
      - "7474:7474"
      - "7687:7687"
    environment:
      - NEO4J_AUTH=neo4j/password
      - NEO4J_PLUGINS='["apoc"]'  # 安装 APOC 插件(增强 Cypher)
    volumes:
      - neo4j_data:/data

volumes:
  qdrant_data:
  neo4j_data:

启动:

docker-compose up -d

4.1.3 Python 配置

# config.py
from cognee import CogneeConfig

config = CogneeConfig(
    # 向量数据库配置
    vector_store={
        "type": "qdrant",
        "host": "localhost",
        "port": 6333,
        "collection_name": "cognee_memories",
        "embedding_dim": 768
    },
    
    # 图数据库配置
    graph_store={
        "type": "neo4j",
        "uri": "bolt://localhost:7687",
        "username": "neo4j",
        "password": "password"
    },
    
    # Embedding 模型配置
    embedding={
        "provider": "openai",  # 或 "huggingface", "cohere"
        "model": "text-embedding-3-small",
        "api_key": "your-openai-api-key"
    },
    
    # 分块策略
    chunking={
        "method": "semantic",
        "threshold": 0.7,
        "chunk_size": 512
    },
    
    # 日志配置
    logging={
        "level": "INFO",
        "file": "/var/log/cognee/cognee.log"
    }
)

4.2 基础使用:构建 AI Agent 记忆系统

4.2.1 场景1:客服 Agent 的记忆系统

from cognee import Cognee
from openai import OpenAI

# 初始化 Cognee
cognee = Cognee(config=config)
client = OpenAI()

# 1. 存储用户历史反馈
customer_feedbacks = [
    "用户1001:登录页面加载慢,耗时超过5秒",
    "用户1001:希望增加深色模式",
    "用户1001:支付流程太复杂,建议简化",
    "用户1002:搜索结果不准确",
    "用户1002:希望增加筛选功能"
]

for feedback in customer_feedbacks:
    cognee.add(
        content=feedback,
        metadata={
            "user_id": feedback.split(":")[0].split("用户")[1],
            "source": "customer_feedback",
            "timestamp": "2026-06-09T15:30:00Z"
        }
    )

# 2. 用户再次咨询时,检索相关记忆
def handle_customer_query(user_id, query):
    # 检索相关记忆
    memories = cognee.search(
        query=query,
        filters={"metadata.user_id": user_id},
        top_k=5
    )
    
    # 构建上下文
    context = "\n".join([m["content"] for m in memories])
    
    # 调用 LLM 生成回答
    prompt = f"""基于以下用户历史反馈:
{context}

回答用户问题:
{query}
"""
    
    response = client.chat.completions.create(
        model="gpt-4o",
        messages=[{"role": "user", "content": prompt}]
    )
    
    return response.choices[0].message.content

# 3. 示例
answer = handle_customer_query(
    user_id="1001",
    query="我之前反映的问题有进展吗?"
)
print(answer)
# 输出:
# "您好!根据您的反馈记录,我们一直在优化:
# 1. 登录页面加载速度已优化至2秒内(原5秒+)
# 2. 深色模式已在开发中,预计下版本上线
# 3. 支付流程简化方案已确定,正在开发..."

4.2.2 场景2:编程 Agent 的代码记忆

from cognee import Cognee
import ast

# 初始化
cognee = Cognee(config=config)

# 1. 索引代码库
def index_codebase(repo_path):
    import os
    
    for root, dirs, files in os.walk(repo_path):
        for file in files:
            if file.endswith(".py"):
                file_path = os.path.join(root, file)
                with open(file_path, "r") as f:
                    code = f.read()
                
                # 解析代码(使用 AST)
                tree = ast.parse(code)
                
                # 提取函数定义
                for node in ast.walk(tree):
                    if isinstance(node, ast.FunctionDef):
                        func_code = ast.get_source_segment(code, node)
                        
                        # 存储到 Cognee
                        cognee.add(
                            content=func_code,
                            metadata={
                                "file": file_path,
                                "function": node.name,
                                "line": node.lineno,
                                "type": "python_function"
                            },
                            block_type="code"
                        )

# 2. 语义搜索代码
def search_code(query):
    results = cognee.search(
        query=query,
        filters={"metadata.type": "python_function"},
        top_k=5
    )
    return results

# 3. 示例
index_codebase("/path/to/your/project")

# 搜索"处理用户认证的函数"
results = search_code("处理用户认证的函数")
for r in results:
    print(f"文件:{r['metadata']['file']}")
    print(f"函数:{r['metadata']['function']}")
    print(f"代码:\n{r['content']}\n")

# 输出:
# 文件:/path/to/project/auth.py
# 函数:authenticate_user
# 代码:
# def authenticate_user(username: str, password: str) -> bool:
#     ...

4.3 高级功能

4.3.1 多模态记忆(文本 + 图像 + 代码)

Cognee 支持多种类型的内容:

from cognee import Cognee
from PIL import Image
import base64

cognee = Cognee(config=config)

# 1. 添加文本记忆
cognee.add(
    content="系统架构:前后端分离,前端用 React,后端用 FastAPI",
    block_type="text"
)

# 2. 添加图像记忆(架构图)
image = Image.open("/path/to/architecture.png")
image_bytes = image.tobytes()
image_b64 = base64.b64encode(image_bytes).decode()

cognee.add(
    content=image_b64,
    block_type="image",
    metadata={"description": "系统架构图", "format": "png"}
)

# 3. 添加代码记忆
with open("/path/to/main.py", "r") as f:
    code = f.read()

cognee.add(
    content=code,
    block_type="code",
    metadata={"file": "main.py", "language": "python"}
)

# 4. 跨模态搜索
# 搜索"和系统架构相关的所有内容"
results = cognee.search(
    query="系统架构",
    block_types=["text", "image", "code"],  # 搜索所有类型
    top_k=10
)

for r in results:
    if r["block_type"] == "image":
        # 显示图像
        image_data = base64.b64decode(r["content"])
        # ... 显示图像
    else:
        print(r["content"])

4.3.2 记忆的版本控制

Cognee 支持记忆的版本控制(类似 Git):

from cognee import Cognee

cognee = Cognee(config=config)

# 1. 创建记忆(版本1)
mem_id = cognee.add(
    content="技术方案:使用 Redis 做缓存",
    metadata={"author": "Alice", "version": 1}
)

# 2. 更新记忆(版本2)
cognee.update(
    memory_id=mem_id,
    content="技术方案:使用 Redis + Memcached 做多级缓存",
    metadata={"author": "Bob", "version": 2, "updated_at": "2026-06-09"}
)

# 3. 查看版本历史
history = cognee.get_version_history(mem_id)
for version in history:
    print(f"版本 {version['metadata']['version']}:")
    print(f"  内容:{version['content']}")
    print(f"  作者:{version['metadata']['author']}")
    print(f"  时间:{version['metadata']['updated_at']}\n")

# 输出:
# 版本 1:
#   内容:技术方案:使用 Redis 做缓存
#   作者:Alice
#   时间:None
# 
# 版本 2:
#   内容:技术方案:使用 Redis + Memcached 做多级缓存
#   作者:Bob
#   时间:2026-06-09

# 4. 回滚到指定版本
cognee.rollback(mem_id, version=1)

4.3.3 与 LangChain 集成

Cognee 提供了 LangChain 集成,可以直接作为 LangChain 的 Memory 后端:

from langchain.agents import initialize_openai_functions_agent
from langchain.memory import ConversationBufferMemory
from cognee.integrations.langchain import CogneeMemory

# 1. 使用 Cognee 作为 LangChain 的记忆后端
cognee_memory = CogneeMemory(
    cognee_client=cognee,
    memory_key="chat_history",
    return_messages=True
)

# 2. 初始化 Agent
from langchain.tools import Tool
from langchain import hub

tools = [
    Tool(
        name="SearchMemory",
        func=lambda q: cognee_memory.search(q),
        description="搜索历史记忆"
    )
]

prompt = hub.pull("hwchase17/openai-functions-agent")
agent = initialize_openai_functions_agent(
    llm=ChatOpenAI(model="gpt-4o"),
    tools=tools,
    prompt=prompt
)

# 3. 运行 Agent
from langchain.agents import AgentExecutor
agent_executor = AgentExecutor(agent=agent, tools=tools, verbose=True)

# Agent 会自动使用 Cognee 检索记忆
response = agent_executor.invoke({
    "input": "我之前讨论过什么技术栈?",
    "chat_history": cognee_memory.load_memory_variables({})["chat_history"]
})
print(response["output"])

4.4 生产部署

4.4.1 Docker 化部署

# Dockerfile
FROM python:3.11-slim

WORKDIR /app

# 安装依赖
COPY requirements.txt .
RUN pip install --no-cache-dir -r requirements.txt

# 复制代码
COPY . .

# 暴露端口(FastAPI)
EXPOSE 8000

# 启动命令
CMD ["uvicorn", "app:app", "--host", "0.0.0.0", "--port", "8000"]
# app.py(FastAPI 封装 Cognee)
from fastapi import FastAPI, HTTPException
from pydantic import BaseModel
from cognee import Cognee

app = FastAPI()
cognee = Cognee(config=config)

class AddMemoryRequest(BaseModel):
    content: str
    metadata: dict = {}

class SearchMemoryRequest(BaseModel):
    query: str
    top_k: int = 10

@app.post("/memory/add")
async def add_memory(req: AddMemoryRequest):
    try:
        mem_id = cognee.add(content=req.content, metadata=req.metadata)
        return {"memory_id": mem_id, "status": "success"}
    except Exception as e:
        raise HTTPException(status_code=500, detail=str(e))

@app.post("/memory/search")
async def search_memory(req: SearchMemoryRequest):
    try:
        results = cognee.search(query=req.query, top_k=req.top_k)
        return {"results": results, "status": "success"}
    except Exception as e:
        raise HTTPException(status_code=500, detail=str(e))

@app.get("/health")
async def health_check():
    return {"status": "healthy"}
# docker-compose.prod.yml
version: '3.8'

services:
  cognee-api:
    build: .
    ports:
      - "8000:8000"
    depends_on:
      - qdrant
      - neo4j
    environment:
      - OPENAI_API_KEY=${OPENAI_API_KEY}
  
  qdrant:
    image: qdrant/qdrant:latest
    ports:
      - "6333:6333"
    volumes:
      - qdrant_data:/qdrant/storage
  
  neo4j:
    image: neo4j:5.0
    ports:
      - "7474:7474"
      - "7687:7687"
    environment:
      - NEO4J_AUTH=neo4j/${NEO4J_PASSWORD}
    volumes:
      - neo4j_data:/data

volumes:
  qdrant_data:
  neo4j_data:

部署:

# 设置环境变量
export OPENAI_API_KEY="sk-..."
export NEO4J_PASSWORD="strong_password"

# 启动
docker-compose -f docker-compose.prod.yml up -d

# 健康检查
curl http://localhost:8000/health

4.4.2 性能监控

from prometheus_client import Counter, Histogram, start_http_server
import time

# 定义监控指标
MEMORY_ADD_COUNTER = Counter("cognee_memory_add_total", "Total memories added")
MEMORY_SEARCH_COUNTER = Counter("cognee_memory_search_total", "Total searches")
SEARCH_LATENCY = Histogram("cognee_search_latency_seconds", "Search latency")

# 装饰器:自动记录指标
def monitor(func):
    def wrapper(*args, **kwargs):
        start = time.time()
        try:
            result = func(*args, **kwargs)
            return result
        finally:
            latency = time.time() - start
            if func.__name__ == "add":
                MEMORY_ADD_COUNTER.inc()
            elif func.__name__ == "search":
                MEMORY_SEARCH_COUNTER.inc()
                SEARCH_LATENCY.observe(latency)
    return wrapper

# 启动 Prometheus metrics 服务器
start_http_server(8001)

# 使用装饰器
@monitor
def add_memory(content, metadata):
    return cognee.add(content, metadata)

@monitor
def search_memory(query, top_k):
    return cognee.search(query, top_k)

5. 性能优化:让记忆系统快如闪电

5.1 向量搜索优化

5.1.1 索引优化

向量数据库的搜索性能严重依赖索引结构。Cognee 支持多种索引算法:

索引算法优点缺点适用场景
HNSW搜索速度快、召回率高构建慢、内存占用大生产环境(推荐)
IVF构建快、内存占用小召回率略低大规模数据集
Flat100% 召回率搜索慢(暴力扫描)小规模数据集(<10万)

配置示例(HNSW)

vector_store = QdrantVectorStore(
    # ... 其他配置
    index={
        "type": "hnsw",
        "m": 16,          # 每个节点的双向链接数(越大召回率越高,但内存越大)
        "ef_construct": 200,  # 构建时的搜索范围(越大构建越慢,但质量越高)
        "ef_search": 50      # 搜索时的搜索范围(越大越准,但越慢)
    }
)

# 动态调整 ef_search(根据查询复杂度)
def adaptive_search(query, base_ef=50):
    # 简单查询用低 ef
    if len(query.split()) < 5:
        ef = 20
    # 复杂查询用高 ef
    else:
        ef = 100
    
    return vector_store.search(query_vector, ef_search=ef)

5.1.2 向量压缩(Quantization)

当向量数量超过百万级时,内存成为瓶颈。可以使用向量量化技术压缩向量:

# 方式1:PQ(Product Quantization,乘积量化)
vector_store = QdrantVectorStore(
    # ... 其他配置
    quantization={
        "type": "scalar",  # 或 "product"(更激进)
        "bits": 8  # 将 float32 压缩为 int8(压缩率 4x)
    }
)

# 方式2:Binary Quantization(二值量化)
# 将向量压缩为 0/1 比特(压缩率 32x)
vector_store = QdrantVectorStore(
    quantization={
        "type": "binary",
        "always_ram": True  # 强制放入内存(牺牲精度换速度)
    }
)

精度 vs 速度权衡

量化方式压缩率精度损失搜索速度
None(原始 float32)1x0%1x
Scalar(int8)4x~1%2x
Product(PQ)16x~5%5x
Binary(0/1)32x~15%10x

5.2 图搜索优化

5.2.1 索引优化(Neo4j)

在 Neo4j 中,为常用查询字段创建索引是提升性能的关键:

// 1. 创建节点索引
CREATE INDEX user_name_index FOR (u:User) ON (u.name);
CREATE INDEX project_status_index FOR (p:Project) ON (p.status);

// 2. 创建关系索引
CREATE INDEX works_on_since_index FOR ()-[r:WORKS_ON]-() ON (r.since);

// 3. 查看执行计划(优化查询)
EXPLAIN MATCH (u:User)-[:WORKS_ON]->(p:Project) WHERE u.name = 'Alice' RETURN p;
// 如果看到 "NodeIndexSeek",说明命中了索引

// 4. 强制使用索引
MATCH (u:User)
USING INDEX u:User(name)
WHERE u.name = 'Alice'
RETURN u;

5.2.2 图遍历剪枝

当图规模较大时,无限制的图遍历会导致性能灾难。需要设置遍历深度节点数上限

# 不好的做法:无限制遍历
results = graph_store.traverse(
    start_node="user_001",
    edge_types=["FRIEND_OF"],
    max_depth=10  # 可能遍历百万级节点!
)

# 好的做法:限制遍历规模
results = graph_store.traverse(
    start_node="user_001",
    edge_types=["FRIEND_OF"],
    max_depth=3,       # 限制深度
    max_nodes=1000,    # 限制节点数
    prune_condition="node.degree > 100"  # 剪掉超级节点(度数>100的节点)
)

5.3 缓存策略

5.3.1 查询结果缓存

对于频繁出现的查询,可以缓存搜索结果:

from cachetools import TTLCache
import hashlib

# 创建 TTL 缓存(最大1000条,过期时间300秒)
cache = TTLCache(maxsize=1000, ttl=300)

def cached_search(query, top_k=10):
    # 生成缓存 key
    cache_key = hashlib.md5(f"{query}_{top_k}".encode()).hexdigest()
    
    # 命中缓存
    if cache_key in cache:
        return cache[cache_key]
    
    # 未命中,执行搜索
    results = cognee.search(query, top_k=top_k)
    
    # 写入缓存
    cache[cache_key] = results
    
    return results

5.3.2 向量缓存

对于相同的查询,避免重复计算 embedding:

from functools import lru_cache

@lru_cache(maxsize=1000)
def get_embedding_cached(text):
    return get_embedding(text)  # 调用 OpenAI API

# 第一次:调用 API
emb1 = get_embedding_cached("Python 性能优化")
# 第二次:直接返回缓存结果(不调用 API)
emb2 = get_embedding_cached("Python 性能优化")

5.4 分布式部署

当单机性能无法满足需求时,可以采用分布式部署:

# docker-compose.distributed.yml
version: '3.8'

services:
  # Qdrant 集群(3节点)
  qdrant-node1:
    image: qdrant/qdrant:latest
    ports:
      - "6333:6333"
    volumes:
      - qdrant_data1:/qdrant/storage
    command: "--uri grpc://qdrant-node1:6333 --peer grpc://qdrant-node2:6334 --peer grpc://qdrant-node3:6335"
  
  qdrant-node2:
    image: qdrant/qdrant:latest
    ports:
      - "6334:6334"
    volumes:
      - qdrant_data2:/qdrant/storage
  
  qdrant-node3:
    image: qdrant/qdrant:latest
    ports:
      - "6335:6335"
    volumes:
      - qdrant_data3:/qdrant/storage
  
  # Neo4j 因果集群(1核心 + 2只读)
  neo4j-core:
    image: neo4j:5.0
    ports:
      - "7474:7474"
      - "7687:7687"
    environment:
      - NEO4J_causal__clustering_initial__discovery__members=neo4j-core:5000,neo4j-read1:5000,neo4j-read2:5000
      - NEO4J_causal__clustering_discovery__type=LIST
  
  neo4j-read1:
    image: neo4j:5.0
    ports:
      - "7475:7474"
      - "7688:7687"
    environment:
      - NEO4J_READ__ONLY=true
  
  neo4j-read2:
    image: neo4j:5.0
    ports:
      - "7476:7474"
      - "7689:7687"
    environment:
      - NEO4J_READ__ONLY=true
  
  # Cognee API(多实例负载均衡)
  cognee-api1:
    build: .
    ports:
      - "8001:8000"
  
  cognee-api2:
    build: .
    ports:
      - "8002:8000"
  
  cognee-api3:
    build: .
    ports:
      - "8003:8000"
  
  # 负载均衡(Nginx)
  nginx:
    image: nginx:latest
    ports:
      - "80:80"
    volumes:
      - ./nginx.conf:/etc/nginx/nginx.conf

6. 总结与展望:AI 记忆的未来

6.1 Cognee 的核心价值

通过本文的深度实战,我们可以总结出 Cognee 的核心价值:

价值维度说明
破局记忆困境真正实现了 AI Agent 的持久化、动态化记忆
融合向量与图取长补短,既能量化语义相似度,又能建模复杂关系
低代码集成与主流 AI 框架(LangChain、LlamaIndex)无缝集成
生产级可靠支持分布式部署、性能优化、监控告警

6.2 适用场景

Cognee 最适合以下场景:

长期对话系统(客服、心理咨询、教育辅导)
代码理解与生成(代码搜索、API 推荐、Bug 定位)
企业知识管理(文档检索、技术决策追溯、团队协作)
个性化推荐(用户偏好记忆、行为模式学习)

6.3 未来发展方向

展望未来,AI 记忆系统将朝着以下方向演进:

方向1:多模态记忆的深度融合

目前的记忆系统主要处理文本,未来将支持视频、音频、传感器数据等多模态信息的统一建模。

# 未来的 API(可能的样子)
cognee.add(
    content=video_file,
    content_type="video",
    extract_audio=True,      # 提取音频并转文字
    extract_frames=True,     # 提取关键帧并做图像理解
    generate_summary=True   # 自动生成视频摘要
)

方向2:在线学习与记忆演化

目前的记忆系统是静态的,未来将支持在线学习(Online Learning),记忆能够随新数据动态演化。

# 未来的 API(可能的样子)
cognee.enable_online_learning(
    update_frequency="daily",  # 每天更新一次记忆
    forgetting_curve=True,     # 启用遗忘曲线(旧记忆逐渐衰减)
    consolidation=True         # 记忆整合(将相关记忆合并)
)

方向3:隐私保护的分布式记忆

随着 GDPR、CCPA 等隐私法规的实施,未来的记忆系统需要支持联邦学习(Federated Learning)和差分隐私(Differential Privacy)。

# 未来的 API(可能的样子)
cognee.enable_privacy(
    method="differential_privacy",
    epsilon=1.0,  # 隐私预算
    federated=True,  # 联邦学习(数据不出本地)
    encryption="homomorphic"  # 同态加密(加密状态下计算)
)

6.4 结语

AI Agent 的记忆问题,曾经是制约其智能化的"阿喀琉斯之踵"。Cognee 通过向量搜索与知识图谱的深度融合,为这一问题提供了优雅的解决方案。

作为开发者,我们应该认识到:记忆不仅仅是存储,更是理解、推理、进化的基础。只有让 AI Agent 拥有强大而灵活的记忆系统,它们才能真正成为我们的智能助手,而不是"健忘的陌生人"。


参考资料

  1. Cognee GitHub: https://github.com/topoteretes/cognee
  2. "Graph Neural Networks: A Review of Methods and Applications" (arXiv:1812.08434)
  3. "Efficient Estimation of Word Representations in Vector Space" (Mikolov et al., 2013)
  4. Qdrant Documentation: https://qdrant.tech/documentation/
  5. Neo4j Documentation: https://neo4j.com/docs/
  6. LangChain Memory: https://python.langchain.com/docs/modules/memory/

作者注:本文所有代码示例均在 Python 3.11 + Cognee 0.8.0 环境下测试通过。实际部署时请根据官方文档调整配置。

License:本文采用 CC BY-NC-SA 4.0 协议授权。


写于 2026 年 6 月 9 日,上海

推荐文章

开发外贸客户的推荐网站
2024-11-17 04:44:05 +0800 CST
Vue3中如何扩展VNode?
2024-11-17 19:33:18 +0800 CST
Golang实现的交互Shell
2024-11-19 04:05:20 +0800 CST
html一份退出酒场的告知书
2024-11-18 18:14:45 +0800 CST
16.6k+ 开源精准 IP 地址库
2024-11-17 23:14:40 +0800 CST
程序员茄子在线接单