Retrieval: подгружать по требованию, а не грузить заранее
На всех схемах RAG-систем есть стрелка от источников контекста к окну. Leonie Monigatti из Elastic в докладе «Agentic Search for Context Engineering» замечает, что эту стрелку рисуют все, а обсуждает почти никто: за ней прячется набор поисковых инструментов, и именно он решает, что окажется в окне. Её оценка — «context engineering это на 80% agentic search» — это hot take без измерений под собой, но рамка рабочая: если ты не спроектировал поиск, ты не спроектировал контекст.
Retrieval: подгружать по требованию, а не грузить заранее
Сдвиг последних месяцев в том, что решение «что искать» переехало от системы к агенту. Marina Wyss формулирует водораздел так: в классическом RAG пайплайн статичен — пришёл вопрос, достали документы, положили в промпт, модель в отборе не участвует. В agentic RAG агент сам решает, что искать, каким инструментом и когда информации достаточно. Разница практическая: в многошаговой задаче релевантность меняется на каждом шаге, и заранее собранный пакет документов протухает уже ко второму ходу.
Три режима отказа
Monigatti перечисляет три способа сломать агентный поиск. Первый — агент вообще не вызывает инструмент: решает, что знает ответ из параметрической памяти. Второй — вызывает не тот инструмент. Она приводит кейс коллеги, где самым сложным в проекте оказалось заставить агента ходить в базу знаний вместо web search. Третий — вызывает нужный инструмент с неверными параметрами.
Третий режим она раскладывает по сложности: get_customer_by_id с одним валидным ID — легко; semantic search со строкой — легко; добавь фильтры и top-K — сложнее; заставь написать полный запрос на ESQL или SQL с нуля — «большинство справляется, некоторые нет». Отсюда прямое проектное следствие: чем слабее модель, тем более специализированные инструменты ей нужны. Более мощная модель, по её словам, «очень сильно» снижает error rate на параметрах, но не гарантирует их отсутствия.
Semantic search проваливается на глазах
Дальше в докладе идут два живых провала, и они полезнее любой теории.
Что произошло: поиск не нашёл то, что лежало в базе
- Кто: Leonie Monigatti, Elastic — живое демо на данных расписания конференции.
- Что делали: сначала semantic search с жёстким
top_k=3по запросу «GAIA», потом general-purpose инструмент, которому агент сам пишет ESQL-запрос. - Результат: семантический поиск вернул доклад про модели Gemma (близко токенизационно), доклад про harness engineering и третий нерелевантный — 0 из 3 попаданий при том, что нужный доклад в базе был. Агент с ESQL написал валидно выглядящий запрос с
%GAIA%, но в ESQL wildcard — это*, а не%(привычка из SQL). Синтаксической ошибки нет, результатов — ноль. Починил ситуацию крошечный custom skill по ESQL: frontmatter инжектится в системный промпт, тело подгружается при обращении, внутри — структура запроса и правила про кавычки и wildcard. После этого корректный запрос с первой попытки. - Вывод: semantic search бесполезен для точных ключей и не фильтрует по метаданным, если те не эмбеддятся (день, зал, спикер — это фильтры, а не смысл). А главный проектный вопрос звучит так: «0 результатов» — это валидный ответ или failure mode? Агент сам этого не различает.
Это не изолированный случай. Lance Martin (LangChain), пересказывая пост CEO Windsurf, приводит ту же мысль про код-агентов: «pure embedding based search становится ненадёжным», поэтому у них комбинация grep, file search, knowledge graph и LLM-реранкинга поверх, а чанкование идёт по семантически осмысленным границам кода.
Отсюда принцип, который Monigatti называет low floor и high ceiling. Нужны и специализированные инструменты (low floor: агент пользуется из коробки, редко ошибается, одна итерация), и general-purpose (high ceiling: вытягивает неожиданные запросы, но требует больше итераций). «Искать одну серебряную пулю — неправильный путь». В Q&A она ссылается на эксперимент Vercel «testing if bash is all you need»: DB-инструмент эффективнее на аналитике, file search быстрее для «просто найти», а наивысшую точность дал гибрид — сначала запрос к БД, потом верификация через shell. Google Cloud говорит то же: на «грязных» логах гибридный поиск часто выигрывает у чистых эмбеддингов.
Отбор инструментов — это тоже retrieval
Легко забыть, что определения инструментов лежат в том же окне, что и документы. Статья RAG-MCP (2025), на которую ссылаются и Marina Wyss, и Carly Richmond из Elastic, предлагает делать семантический поиск по описаниям инструментов и подгружать только релевантные текущему шагу. Цифры: точность выбора инструмента выросла с 14% до 43% при сокращении prompt-токенов примерно вдвое (в изложении Elastic — «более чем на 50%»). Тот же приём реализован в langgraph-bigtool у LangChain. Оговорка честная: нужен он, когда инструментов десятки. При пяти-десяти избыточен.
Ручной вариант дешевле и работает сразу. Carly Richmond показывает пример из Elastic Agent Builder, где агенту выдано 5 инструментов из 24 доступных — и по безопасности, и чтобы не путать модель: чем шире пространство решения, тем чаще выбирается не тот инструмент.
Третья ручка — время жизни накопленного. В её же демо долгой памяти счётчик показывал 30 сообщений в индексе. Temporal pruning (удалить всё старше двух недель) срезал 15, оставив 15 — ровно вдвое. Смысл здесь шире экономии места: устаревшие записи возвращаются в выдачу и отравляют контекст.
И четвёртая, самая неприятная. В том же демо Richmond заглянула в индекс и обнаружила, что система раз за разом сохраняла и возвращала один и тот же итинерарий — по одному признаку нашлось 12 совпадений. Без дедупликации автоматическая память сама себя усиливает: агент видит одно и то же в двенадцати экземплярах и считает это подтверждением. Рядом лежит забываемая ручка размера выдачи: в демо стоял size=20, и автор тут же себя поправила — «возможно, стоит вернуть один-два».
Что грузить заранее и что по требованию
Практика Anthropic в Claude Code, как её пересказывает Marina Wyss, — гибрид: claude.md грузится вперёд, в начале каждой сессии, а навигация по кодовой базе идёт по требованию через glob и grep. Кодовая база не индексируется заранее, агент исследует её по мере надобности. Общая философия — «делать самое простое, что работает».
Тот же принцип в терминах DataRobot: в контекст загружаются только метаданные skills, и работают они как индекс в базе данных — агент по ним находит нужное, а тело подгружает при обращении. Их оценка — «минимум в десять раз меньше» операционного объёма, чем при прямом подключении MCP.
Бытовой замер того же эффекта есть у Jono Catliff: транскрипт на 3001 строку, вставленный сообщением в чат, съел 71% окна. Тот же материал, сохранённый файлом и прочитанный агентом по пути, — 38%. Замер без методологии, брать как порядок величины, но направление верное: ссылка на файл дешевле содержимого файла. Промышленный вариант той же идеи предлагает Ian Gotts — держать контекст во внешней базе (граф или онтология) и поднять над ней MCP-сервер. Он же оговаривает, что устоявшихся best practices здесь пока нет ни у кого.
Честная граница: холистические запросы RAG не берёт
Это место, где принято обещать больше, чем система может.
Dan Biderman (Engram), опираясь на работу с юридическими файловыми системами Harvey, приводит запрос: «какие M&A-сделки мы в этом году не закрыли?» Ответа нет ни в одном чанке — нигде не написано «не завершено». Надо пройти клиентское дело за делом, снять суть и понять, что петля не закрыта. Поиск по сходству к таким вопросам неприменим по конструкции: он находит то, что в данных записано, и не способен увидеть отсутствующее. По его словам, на фронтир-моделях с компакцией такой запрос обходится в тысячи долларов за один прогон — при том что любой сотрудник ответил бы сам.
Zach Blumenfeld (Neo4j) называет тот же класс estate-level: «какой документации у нас нет», «что мы вообще не используем», «какие паттерны повторяются по всему корпусу». Такие вопросы требуют обхода всего датасета, а каждый дополнительный векторный хит — ещё один шанс промахнуться мимо нужного документа. Он же честно говорит, что граф здесь дополняет семантический поиск.
Есть и менее очевидный отказ. Nyah Macklin (Neo4j) разбирает случай, где retrieval сработал безупречно: комплаенс-агент вытащил три верных чанка — «Jessica работает в Apex Global», «Apex Global в санкционном списке», «Jessica просит увеличение кредитной линии на $25 000». Все три лежали в окне одновременно. Агент одобрил. Данные верные, поиск верный, а связь между фактами нигде не была представлена. Её формулировка: лучшие модели так же бессильны перед раздробленным контекстом — они лишь рассуждают над обломками. Отсюда тезис о второй, незастроенной оси: текущий retrieval работает по текстовому сходству, которое даёт, по её оценке, «70–80% пути». Вторая ось — структурное сходство. Ей посвящена четвёртая часть серии.
Практика: индексы, префильтры, детерминированная загрузка
Инженерный минимум описывает Carly Richmond: чанкование, эмбеддинги, векторная БД, приближённый kNN — в её примере HNSW с параметром num_candidates на шард. На миллионах векторов запрос становится долгим, отсюда prefiltering: сузить пространство лексическим или атрибутным фильтром до векторного сравнения — например, взять только записи за последнюю неделю. Чаще всего это самый дешёвый прирост точности. Она же призывает не бояться lexical: в собственном инструменте get_flights она сознательно использует лексический поиск, потому что пункты отправления и назначения нужны точные. Поверх выдачи ставится re-ranking — отдельный класс моделей, переоценивающих документы по своим признакам. Qwen, Jina, mixedbread лежат публично на Hugging Face.
Векторного стека можно и не поднимать. Zach Blumenfeld построил рабочую систему вообще без него: Lucene-индекс ставится только на ноды с текстом (документы и секции, папки не индексируются), каждому узлу выдаётся иерархический URI вида technical-library/bulletins/<doc>/<section>, и поиск скоупится пост-фильтром WHERE uri STARTS WITH ... — «искать только внутри раздела recalls». Вместо эмбеддингов — semantic expansion: модель расширяет запрос своим знанием мира (по запросу «engine shuttering» искать также «misfire» и «rough idle») и скармливает это Lucene как OR-запрос. Мотив прагматичный: он работает с шестью вендорами векторных БД и не хочет привязки. Оговорки он тоже называет: пост-фильтр не заменяет пре-фильтр, и выигрыш меньше на плохо озаглавленных данных.
Загрузка документов у него детерминированная, без LLM: containment-дерево из уровней library, folder, document и section, NEXT_SECTION для порядка, LINKS_TO для перекрёстных ссылок, парсинг обычным regex/NLP. Отдача — идемпотентность: «если граф завтра исчезнет, а документы не менялись, перезальёшь и получишь ровно тот же граф». Работает потому, что исходные PDF и markdown уже структурированы. На грязных источниках понадобится LLM-парсинг. Ловушка — переименование документа: чужие ссылки на его URI протухают, и связи надо чинить руками.
Что с этим делать
Начни с описаний инструментов. Структура описания по Monigatti — core purpose, затем trigger conditions (когда использовать и когда НЕ использовать), затем relationships — стоит ноль и снимает часть промахов выбора инструмента.
Сократи набор инструментов до необходимого. 5 из 24, как в примере Elastic Agent Builder, сужают пространство ошибки. Если инструментов десятки, ставь семантический поиск по их описаниям (RAG-MCP: рост точности с 14% до 43% при вдвое меньших токенах).
Заведи префильтр раньше, чем реранкер. Отсечь по дате, типу, владельцу до векторного сравнения дешевле, чем переранжировать мусор. И не стесняйся лексического поиска там, где нужны точные значения.
Обслуживай индекс как код. Дедупликация (12 одинаковых записей — реальный дефект, а не гипотеза), temporal pruning старше N недель, явный лимит выдачи (size=20 почти всегда больше, чем нужно).
Грузи файлы по пути. Тела skills и документов подтягивай при обращении, а в стартовый контекст клади только индекс.
Определи заранее, что твоя система не умеет. Возьми один холистический вопрос из своего домена («какие сделки мы не закрыли») и проверь на нём retrieval. Если он не отвечает, зафиксируй это как известную границу до того, как её обнаружит пользователь.
Построим такой контур в вашей компании
coMind переводит команды и компании в AI-Native: первый контур за 30 дней, методика — в книгах серии «Путь компании к AI-Native».