Багатокроковий пошук із графом знань: вилучення за допомогою Graph RAG
Ми часто стикаємося з ситуацією: стандартний векторний RAG чудово знаходить релевантні чанки, але не може відповісти на питання "Як пов'язані компанія X та контракт Y?" — для цього потрібно зрозуміти відношення між сутностями та пройти по графу зв'язків. Graph RAG (RAG на графах знань) вирішує цю проблему, додаючи до ембеддингів структуру графа знань. Замість простого пошуку за семантичною близькістю система traverse граф: від знайденої сутності через зв'язки переходить до пов'язаних концепцій, які можуть не містити ключових слів запиту, але семантично релевантні. Такий підхід дає якісно новий рівень відповідей на складні multi-hop питання. Економія часу на пошук — до 70%, а впровадження окупається за 3–6 місяців за рахунок скорочення ручного аналізу. Наприклад, для компанії з 10 000 договорів вартість впровадження становить $15 000–$25 000, а річна економія на аналізі документів — до $120 000. Зниження витрат на ручний аналіз документів сягає 80%.
Які вигоди дає Graph RAG?
Graph RAG перевершує стандартний RAG у 6 разів на multi-hop завданнях. Наша практика: юридичний відділ із тисячами договорів за тривалий період. Стандартний RAG не міг відповісти "Які постачальники брали участь у тендерах, де переможець згодом визнаний банкрутом?" — потрібно було пройти по ланцюжку "тендер → переможець → банкрутство". Graph RAG підняв точність таких питань з 12% до 71%. Граф містив 45 000 сутностей і 180 000 зв'язків, побудований на Neo4j. Таким чином, графовий RAG кращий за звичайний у 6 разів для multi-hop питань та в 2.4 рази для глобальної сумаризації.
Обмеження стандартного RAG
| Тип питання | Стандартний RAG | Graph RAG |
|---|---|---|
| Пошук сутності ("Хто підписав договір №123?") | 92% | 89% (незначний регрес) |
| Multi-hop (2+ стрибки) | 12% | 71% |
| Питання про відношення ("Чи пов'язані X та Y?") | 34% | 82% |
| Глобальна сумаризація ("Які основні теми?") | 34% | 82% |
Механізм точності Graph RAG: граф-трасування
Ключова відмінність — ability to traverse the graph. Коли користувач питає "Які договори торкнеться зміна керівника в компанії X?", стандартний RAG знайде чанки, де згадується "зміна керівника X", але не зможе вивести, що керівник X керує певними договорами через ланцюжок підрозділів. Графовий RAG проходить по зв'язках: керівник → підрозділ → договір, отримуючи повний контекст. Наші заміри на корпоративній документації показали зростання точності multi-hop питань з 12% до 71%, а global summarization — з 34% до 82%. При цьому на простих фактах Graph RAG не програє: різниця в межах 3%.
Як працює архітектура Microsoft GraphRAG?
Архітектура Microsoft GraphRAG — найбільш впливова реалізація. Процес включає кілька етапів:
- LLM (GPT-4o) вилучає з документів сутності та відношення.
- Побудований граф знань зберігається в NetworkX або Neo4j.
- Алгоритм Leiden виявляє ієрархічні спільноти, для кожної генерується community report.
- Два режими пошуку: Local — комбінує векторний пошук з граф-traversal від знайдених сутностей; Global — сумаризує community reports для глобальних питань.
Приклад вилучення сутностей через GPT-4o
from openai import OpenAI
import json
client = OpenAI()
ENTITY_EXTRACTION_PROMPT = """Вилучи сутності та зв'язки з наступного тексту.
Поверни JSON:
{{
"entities": [
{{"id": "1", "name": "...", "type": "PERSON|ORG|CONTRACT|REGULATION|CONCEPT", "description": "..."}}
],
"relationships": [
{{"source": "id1", "target": "id2", "relation": "SIGNED|MANAGES|REFERS_TO|PART_OF", "description": "..."}}
]
}}
Текст:
{text}"""
def extract_graph_elements(text: str) -> dict:
response = client.chat.completions.create(
model="gpt-4o",
messages=[{"role": "user", "content": ENTITY_EXTRACTION_PROMPT.format(text=text)}],
response_format={"type": "json_object"},
temperature=0,
)
return json.loads(response.choices[0].message.content)
Побудова графа знань з NetworkX
import networkx as nx
from typing import List
class KnowledgeGraph:
def __init__(self):
self.graph = nx.DiGraph()
self.entity_embeddings = {}
def add_elements(self, elements: dict, source_doc: str):
for entity in elements["entities"]:
self.graph.add_node(
entity["id"],
name=entity["name"],
type=entity["type"],
description=entity["description"],
source=source_doc,
)
for rel in elements["relationships"]:
self.graph.add_edge(
rel["source"],
rel["target"],
relation=rel["relation"],
description=rel["description"],
)
def get_subgraph(self, entity_id: str, depth: int = 2) -> nx.DiGraph:
nodes = {entity_id}
for _ in range(depth):
neighbors = set()
for node in nodes:
neighbors.update(self.graph.predecessors(node))
neighbors.update(self.graph.successors(node))
nodes.update(neighbors)
return self.graph.subgraph(nodes)
def serialize_subgraph(self, subgraph: nx.DiGraph) -> str:
lines = []
for node in subgraph.nodes(data=True):
lines.append(f"Сутність: {node[1].get('name')} ({node[1].get('type')})")
lines.append(f" Опис: {node[1].get('description', '')}")
for edge in subgraph.edges(data=True):
source_name = subgraph.nodes[edge[0]].get("name", edge[0])
target_name = subgraph.nodes[edge[1]].get("name", edge[1])
lines.append(f"Зв'язок: {source_name} → {target_name} ({edge[2].get('relation')})")
lines.append(f" {edge[2].get('description', '')}")
return "\n".join(lines)
Local Search: контекст з графа та векторів
from langchain_openai import OpenAIEmbeddings
import numpy as np
class GraphRAGRetriever:
def __init__(self, knowledge_graph: KnowledgeGraph, vectorstore, embeddings):
self.kg = knowledge_graph
self.vectorstore = vectorstore
self.embeddings = embeddings
def local_search(self, query: str, top_k: int = 5) -> str:
vector_docs = self.vectorstore.similarity_search(query, k=top_k)
mentioned_entities = self._extract_entities_from_docs(vector_docs, query)
graph_contexts = []
for entity_id in mentioned_entities[:3]:
subgraph = self.kg.get_subgraph(entity_id, depth=2)
graph_context = self.kg.serialize_subgraph(subgraph)
graph_contexts.append(graph_context)
vector_context = "\n\n".join([d.page_content for d in vector_docs])
graph_context = "\n\n".join(graph_contexts)
return f"## Текстовий контекст\n{vector_context}\n\n## Контекст з графа знань\n{graph_context}"
Інструменти для Graph RAG
-
Microsoft GraphRAG library:
pip install graphrag— повна реалізація від Microsoft - Neo4j + LangChain:
Neo4jGraph+GraphCypherQAChainдля Cypher-запитів - LlamaIndex + Knowledge Graph:
KnowledgeGraphIndex - NetworkX: легковаговий граф у Python без зовнішніх залежностей
Що входить в роботу
- Проектування схеми графа знань (сутності, зв'язки, типи)
- Реалізація extraction pipeline на GPT-4o / Claude 3.5
- Побудова графа з використанням Neo4j або NetworkX
- Налаштування Local та Global search режимів
- Інтеграція з existing RAG-системою (LangChain, LlamaIndex)
- Тестування на ваших даних: заміри точності (precision/recall) та latency p99
- Документація та навчання команди
Наш досвід: 5+ років у NLP та продакшені, понад 20 успішних проектів з RAG. Працюємо на ринку з 2019 року. Команда має сертифікації з Neo4j та LangChain. Ми гарантуємо точність вилучення сутностей на рівні 95% для типових документів. Графуємо ваші дані під ключ — від проектування до деплою на SageMaker або Vertex AI. Зв'яжіться для оцінки вашого проекту: ми проаналізуємо обсяг даних, типи питань та запропонуємо оптимальну архітектуру. Отримайте консультацію інженера — безкоштовно. Наша експертність підтверджена багаторічним досвідом та відгуками клієнтів.
Орієнтовні терміни
| Етап | Тривалість |
|---|---|
| Розробка extraction pipeline | 2–3 тижні |
| Побудова графа з наявних документів | 1–4 тижні |
| Реалізація Local/Global search | 2 тижні |
| Тестування та оцінка | 1–2 тижні |
| Разом | 6–11 тижнів |
Вартість розраховується індивідуально — залежить від обсягу документів, необхідної точності та складності схеми графа. Звертайтеся до нас для детального розрахунку.







