Цель лекции
Объяснить, почему зрелые memory systems часто объединяют embeddings, keyword search и графы знаний.
Ожидаемый результат
Читатель понимает, когда простого vector store уже недостаточно, зачем нужны entity linking, knowledge graph, temporal graph, bitemporal memory и как практический retrieval объединяет graph, embeddings и keyword.
Зачем это нужно
Vector search отлично находит смысловую близость. Если пользователь описал проблему другими словами, embeddings часто найдут нужный документ, эпизод или summary.
Но memory systems часто требуют не только "похожий текст", а точные связи:
- какой пользователь работает в каком проекте;
- какой сервис зависит от какого API;
- какой тикет связан с каким клиентом;
- какой файл импортирует какой helper;
- какое решение заменило старое;
- какой документ является canonical;
- какое событие произошло до другого;
- какие сущности участвуют в incident.
Vector search плохо выражает такие строгие отношения. Graph search, наоборот, хорошо работает со связями, но хуже понимает расплывчатый естественный язык.
Зрелые системы часто соединяют оба подхода:
semantic similarity + exact search + entity graph + temporal constraints
Основная идея
Векторный поиск хорошо ловит смысловую близость, а графы лучше представляют строгие связи между сущностями и событиями.
Hybrid Vector-Graph Memory использует:
- embeddings для поиска похожего смысла;
- keyword/BM25 для точных терминов, IDs и paths;
- graph для сущностей и отношений;
- temporal metadata для времени;
- reranking для финального отбора;
- permissions и scopes для безопасности.
Цель гибрида - не усложнить architecture ради красоты, а закрыть разные retrieval failure modes.
Ключевые термины
| Термин | Короткое определение |
|---|---|
Vector memory |
Память, индексированная через embeddings для semantic retrieval. |
Graph memory |
Память, представленная сущностями и связями. |
Hybrid retrieval |
Поиск, объединяющий vector, keyword, graph, temporal и metadata signals. |
Entity linking |
Связывание упоминаний в тексте с конкретными сущностями. |
Knowledge graph |
Граф сущностей, отношений и свойств. |
Temporal graph |
Граф, где связи имеют временные метки или интервалы действия. |
Bitemporal memory |
Модель времени, где различаются время события и время, когда система о нем узнала. |
Path finding |
Поиск цепочки отношений между сущностями. |
Graph expansion |
Расширение результатов через соседние узлы графа. |
Reranking |
Финальный отбор кандидатов после разных retrieval сигналов. |
Ограничения vector search
Vector search слаб там, где важна точность.
Проблемы:
- похожее не всегда полезное;
- exact identifiers могут теряться;
- связи между сущностями неявны;
- сложно ответить "через что A связано с B";
- temporal order не моделируется сам по себе;
- source authority и scope нужно добавлять отдельно;
- conflict detection слаб без structured facts;
- embeddings могут найти устаревший, но похожий chunk.
Пример:
Query:
"Почему export недоступен у клиента?"
Vector search может найти много похожих support cases. Но агенту нужно знать:
- какой именно account;
- какой plan активен сейчас;
- какие feature flags включены;
- какие incidents относятся к этому region;
- имеет ли пользователь доступ к CRM data.
Это graph/metadata problem, не только semantic similarity.
Ограничения graph search
Graph search тоже не универсален.
Проблемы:
- требует entity extraction;
- требует entity linking;
- плохо работает с vague query без сущностей;
- graph может быть неполным;
- связи могут устаревать;
- graph traversal может вернуть слишком много соседей;
- текстовые объяснения всё равно нужно искать в docs;
- построение графа требует governance.
Пример:
User:
"Найди похожие случаи, где агент ошибся из-за слишком узкой проверки."
Если в query нет точных entities, vector search по reflection summaries может быть лучше первого шага. Потом найденные записи можно связать через graph.
Entity linking
Entity linking - мост между текстом и графом.
Raw text:
"invoice totals падает после изменения discount helper"
Entities:
test: invoice_totals.test.ts
file: src/pricing/discount_helper.ts
domain: pricing
concept: invoice totals
Relations:
discount_helper.ts -> affects -> invoice totals
invoice_totals.test.ts -> tests -> invoice totals
discount_helper.ts -> belongs_to -> pricing module
Entity linking должен решать:
- это новый объект или уже известный;
- какие aliases у сущности;
- как различать похожие имена;
- какой scope у entity;
- какой source подтвердил связь.
Без entity linking graph memory быстро превращается в набор разрозненных узлов.
Knowledge graph
Knowledge graph хранит узлы, ребра и свойства.
Пример:
Nodes:
- User
- Project
- Lesson
- Document
- Service
- Test
- Feature
Edges:
- works_on
- contains
- depends_on
- tests
- owns
- supersedes
- conflicts_with
- derived_from
Graph может хранить:
- entities;
- semantic facts;
- project structure;
- service dependencies;
- document relations;
- user/team/org scopes;
- provenance links;
- memory record relationships.
Пример:
Project: AI Agent Memory Guide
contains -> Module 05
Module 05
contains -> Lesson 5.4
Lesson 5.4
follows -> Lesson 5.3
Lesson 5.4
introduces -> Hybrid Vector-Graph Memory
Такой graph помогает retrieval: если пользователь просит "следующую лекцию", система может найти соседние уроки и content plan.
Temporal graph
В memory systems связи меняются во времени.
Пример:
Project -> uses_test_runner -> Jest
valid_until: 2026-07-20
Project -> uses_test_runner -> Vitest
valid_from: 2026-07-20
Temporal graph хранит:
- когда связь была активна;
- когда она изменилась;
- какие события привели к изменению;
- какая версия действовала в момент задачи.
Это важно для:
- historical questions;
- audit;
- debugging old decisions;
- staleness detection;
- update and supersession.
Без temporal metadata graph может уверенно смешивать старые и новые связи.
Bitemporal memory
Bitemporal memory различает два времени:
- когда событие произошло;
- когда система узнала о событии.
Пример:
Project switched to Vitest on 2026-07-20.
Agent learned this from package.json on 2026-08-07.
Эти даты разные.
Почему это важно:
- агент может объяснить, почему раньше использовал old fact;
- audit может восстановить knowledge state агента на момент ответа;
- update может корректно supersede old records;
- исторический retrieval может выбрать правильную версию.
Bitemporal model особенно полезна в enterprise, legal, finance и incident analysis.
Path finding
Path finding ищет цепочку отношений.
Пример вопроса:
"Почему изменение discount_helper.ts повлияло на invoice_totals.test.ts?"
Graph path:
discount_helper.ts
-> calculates -> discount amount
-> used_by -> invoice total calculation
-> tested_by -> invoice_totals.test.ts
Vector search мог найти похожие snippets, но graph объясняет причинную цепочку.
Другой пример:
"Какие документы подтверждают это правило?"
Path:
procedure_record
-> supported_by -> reflection_record
-> derived_from -> event_record
-> source -> test_log
Path finding усиливает explainability.
Практический hybrid retrieval
Такой pipeline не обязательно нужен в MVP. Но он полезен, когда:
- много сущностей;
- важны связи;
- есть разные scopes;
- corpus большой;
- retrieval noise дорог;
- нужно объяснять answers;
- данные меняются во времени.
Graph + embeddings + keyword
Роли сигналов:
| Сигнал | Сильная сторона | Пример |
|---|---|---|
| Embeddings | Смысловая близость | "похожая ошибка проверки" |
| Keyword/BM25 | Точные имена | invoice_totals.test.ts, ERR_403 |
| Graph | Связи entities | file -> module -> test -> incident |
| Temporal | Время и версии | active fact today vs historical fact |
| Metadata | Scope, source, permissions | project_id, account_id, status |
Результат должен объединяться не простым сложением scores, а через task-aware reranking.
Мини-кейс: CRM agent
Support agent отвечает на вопрос:
"Почему клиент не видит export?"
Hybrid retrieval:
- keyword: customer name, account id, feature
export; - graph: account -> plan -> entitlements -> feature flags;
- vector: похожие support cases;
- temporal: текущий plan, recent incidents;
- metadata: permissions, region, product version.
Без graph агент может найти похожий case другого клиента. Без vector он может пропустить похожую known issue. Без temporal он может использовать старый plan.
Мини-кейс: research agent
Research question:
"Что изменилось в API behavior между версиями?"
Hybrid retrieval:
- keyword: API endpoint names, version numbers;
- vector: relevant changelog sections;
- graph: endpoint -> parameters -> deprecations -> migration guide;
- temporal: valid_from for behavior changes;
- source priority: official docs > blog post.
Graph помогает связать endpoint, parameter и migration note. Vector помогает найти релевантное описание даже при другой формулировке.
Мини-кейс: coding agent
Task:
"Тест invoice_totals снова падает после изменения скидок."
Hybrid retrieval:
- keyword finds exact test name;
- graph finds files connected to invoice totals;
- vector finds previous reflections about narrow testing;
- temporal search finds recent related failures;
- metadata filters restrict to current repo;
- reranker selects procedure and current code facts.
Простой vector store может вернуть generic docs about tests. Hybrid retrieval достает actionable context.
Когда hybrid уже нужен
Признаки:
- много entities и relations;
- retrieval по embeddings часто дает похожий шум;
- пользователи спрашивают "почему связано";
- нужно path explanation;
- данные имеют версии и время;
- важны permissions;
- есть multi-tenant;
- corpus содержит code, docs, tickets, CRM;
- one-hop retrieval недостаточен;
- нужно conflict detection.
Если таких признаков нет, hybrid graph architecture может быть overkill. Начинайте проще, но проектируйте representation так, чтобы позже добавить links.
Типичные ошибки
Ошибка 1: ожидать от vector search понимания строгих связей.
Embeddings не заменяют entity relations.
Ошибка 2: строить graph без entity linking.
Граф с дублирующимися сущностями быстро теряет ценность.
Ошибка 3: забывать время.
Связь могла быть true в прошлом и false сейчас.
Ошибка 4: считать graph всегда authoritative.
Graph может быть неполным, stale или derived from weak sources.
Ошибка 5: не объединять с keyword search.
Exact IDs, paths и error codes часто критичны.
Ошибка 6: не делать reranking.
Hybrid retrieval создает candidate pool, но не финальный prompt.
Ошибка 7: не учитывать permissions в graph traversal.
Соседняя сущность может быть недоступна текущему пользователю.
Краткое резюме
Hybrid Vector-Graph Memory объединяет semantic retrieval, exact search и structured relations. Vector search помогает находить похожие смыслы, keyword search - точные идентификаторы, graph - связи между сущностями, temporal metadata - актуальность и историю.
Гибрид особенно полезен для CRM, coding agents, research agents и enterprise search, где агент должен не просто найти похожий текст, а понять отношения, путь, версию, источник и scope.
Вопросы для самопроверки
- Почему vector search плохо выражает строгие связи?
- Что такое entity linking, и зачем он нужен graph memory?
- Чем temporal graph отличается от обычного graph?
- Что дает bitemporal memory?
- Почему hybrid retrieval всё равно требует reranking?
Что дальше
В следующей лекции мы разберем Event-Sourced Agent: паттерн, где источником истины становится append-only журнал событий, из которого можно восстанавливать состояние, строить snapshots и делать replay.