RU
Долговременная память агента: проектирование под то, как память ломается на самом деле

Долговременная память агента: проектирование под то, как память ломается на самом деле

2026-08-07

Дайте кодовому агенту хорошую модель и хорошие инструменты — и он всё равно спросит вас, четвёртый раз за неделю, зачем существует обёртка с ретраями. Он не тупит. Он действительно не знает, потому что ничего из его мира не пережило конец прошлой сессии.

Очевидное решение — файл с заметками, и очевидное решение протухает примерно за три недели. Этот пост о том, почему оно протухает и что строить вместо. Он вырос из слоя памяти в Hilum Tools, который я ежедневно гоняю против мультирепозиторного воркспейса — включая тот, в котором живёт этот сайт.


Режим отказа не тот, о котором вы думаете

Проектируя хранилище памяти, люди оптимизируют recall: найдёт ли агент заметку? Это не та тревога. Провал выборки громкий — агент спрашивает то, на что вы уже отвечали, вы это замечаете, отвечаете снова, жизнь продолжается. Раздражает, но ограничено и самокорректируется.

По-настоящему больно бьёт тихий отказ. Агент находит заметку; заметка неверна, устарела или является одной из пяти почти-копий, которые друг другу противоречат, — и агент действует с полной уверенностью. Вопроса вы не получаете. Вы получаете pull request, построенный на конвенции, от которой отказались два месяца назад, и узнаёте об этом на ревью. Или не узнаёте.

Почти всё это производят два механизма:

Почти-дубликаты дробят выборку. Пять слегка разных заметок про одну конвенцию разрывают сигнал. Каждая по отдельности выглядит авторитетно и несёт свою деталь. Та, что выиграет ранжирование, станет истиной этой сессии, и какая именно — вопрос подбрасывания монетки.

Устаревшие записи обгоняют актуальные. Заметка, написанная по свежим следам решения, подробна, хорошо сформулирована и богата ровно той лексикой, которая есть в вопросе. Её замена лаконична, потому что к тому моменту это уже все знали. Старая выигрывает по любой метрике похожести, какую ни назови. Свежесть — единственный сигнал, который бы вас спас, и именно ему большинство хранилищ даёт наименьший вес.

Оба отказа создаются на записи и лишь проявляются на чтении. Одно это наблюдение задаёт всю конструкцию.

Правило первое: правила работают на записи

Если вы наводите гигиену при чтении, вы пытаетесь чинить уже испорченный корпус — на горячем пути и с бюджетом по задержке. Это не работает и дорого стоит даже в попытке.

Наводите её на записи, где у вас есть время, весь корпус и автор ещё в контуре:

  • Ловить почти-дубликат в момент записи и говорить о нём. Не молча сливать — сообщать. «Это на 0.91 похоже на запись от июня; может, обновить её?» Автор здесь и знает, что из этого правда. Слияние, решённое косинусной близостью, — это догадка, сделанная наименее компетентным для этого компонентом.
  • Архивировать, никогда не удалять. Заменённая запись всё ещё отвечает на вопрос «почему раньше делали иначе» — а это ровно тот вопрос, который всплывает, когда кто-то предлагает снова сделать по-старому. Архивные записи уходят с дефолтного пути выборки и остаются доступными по запросу.
  • Требовать тип. Бестиповый мешок текста не поддаётся рассуждению. Четырёх типов на практике хватает почти на всё, и у каждого свой срок жизни и свой вес в выборке.
ТипЧто несётСрок жизни
РешениеСделанный выбор, альтернативы и почему. Почему — это и есть полезная нагрузка: решение без него просто факт.Долгий. Заменяется, не удаляется.
ГраблиЛовушка, за которую уже заплатили, и симптом, по которому она узнаётся.Долгий. Самый ценный класс на байт.
КонвенцияКак здесь принято, там, где код этого не показывает сам.Средний. Дрейфует, требует пересмотра.
СостояниеЧто в работе, что last-green, что заблокировано.Короткий. Обязано истекать, иначе становится ложью.

С типом «состояние» ошибаются чаще всего. Запись «текущий статус» без срока годности становится активно вредной за считаные дни: это уверенное, конкретное и неправильное описание мира, и ровно на таком агент действует не задумываясь. Либо у неё есть срок, либо она выводится из ground truth (git, CI, трекер), а не хранится.

Правило второе: чтение автоматическое, запись осознанная

Асимметрия здесь и есть суть.

Чтение должно быть бесплатным. Если агенту нужно решать, обращаться ли к памяти, он пропустит её ровно тогда, когда будет под давлением, — то есть ровно тогда, когда она бы помогла. Брифинг приходит на старте сессии, спрашивали его или нет: действующие конвенции, недавние решения, известные грабли в области, которую трогают, текущее состояние. Один вызов, один ответ в бюджете.

Запись должна быть решением. Агент, пишущий заметку после каждой задачи, производит корпус, состоящий преимущественно из пересказанных постановок задач, — и такой корпус хуже, чем никакого: он размывает сигнал и раздувает каждую выборку. Планка записи — один вопрос: ошибётся ли без этого компетентный инженер, пришедший завтра? Ответ «нет» — не пишем.

Отсюда получается короткий список того, чего хранить не нужно никогда, и этот список делает для качества больше, чем любое улучшение ранжирования:

  • Всё, что уже записано в репозитории. Структура кода, раскладка файлов, список зависимостей, что делает функция. Для этого есть кодовая интеллектуальность; дублирование в памяти гарантирует, что копия протухнет, а оригинал — нет.
  • Всё, что уже записано в git. Кто что менял, когда и с каким сообщением.
  • Нарратив сессии. «Попробовал X, не вышло, попробовал Y» — это контекст текущего разговора, а не знание. Оно умирает вместе с сессией, и правильно делает.
  • Всё, что уже лежит в файле правил или в ADR. Ссылаться, а не пересказывать. Пересказанный факт — второй источник истины, а второй источник истины — будущее противоречие.

Правило третье: область — часть записи

Заметка про «нашу конвенцию сообщений коммита» истинна в одном репозитории и ложна в соседнем. Заметка про «как я люблю, чтобы было устроено ревью» истинна во всех репозиториях, к которым этот человек прикасается. Хранение обеих в одной недифференцированной куче означает, что одна из них утечёт в неверный контекст и будет там неправа с полной уверенностью.

Трёх областей достаточно:

  • Репозиторий — едет вместе с репо, разделяется со всеми, кто его клонирует.
  • Хост-глобальная — эта машина, этот оператор, все проекты. Предпочтения, особенности окружения, личный рабочий процесс.
  • Команда / организация — общая между участниками и репозиториями; единственная область, которой нужен контроль доступа.

Ошибитесь здесь — получите две классические жалобы на агентскую память: «он тащит сюда правила другого проекта» и «мне приходится учить его одному и тому же в каждом репозитории».

Правило четвёртое: хранилище отчитывается о собственном здоровье

Память — та единственная подсистема, где доверие и есть продукт. Значит, её нужно уметь инспектировать, и инспекция должна быть достаточно дешёвой, чтобы её реально делали.

Считайте и показывайте: количество записей по типам и областям; число кластеров почти-дубликатов; отношение архивных к активным; распределение по возрасту — в частности, какая доля записей состояния просрочена; и счётчик противоречий — пары активных записей, утверждающих противоположное об одном и том же.

Последнее — это сигнал тревоги. Хранилище с противоречиями — не хранилище с небольшой проблемой качества; это хранилище, каждый ответ которого теперь подбрасывание монетки, и отдавать эти ответы оно будет тем же уверенным тоном, что и раньше.


Что мерить

Честные метрики слоя памяти — поведенческие, а не внутренние:

  • Доля повторных вопросов. Как часто агент спрашивает то, на что корпус уже отвечает. Падает быстро, когда память начинает работать; самый лёгкий выигрыш для демонстрации.
  • Доля повторных ошибок. Как часто наступают на уже записанные грабли. Двигается медленнее, стоит намного больше.
  • Токены холодного старта. Токены между началом сессии и первой полезной правкой. Брифинг должен схлопывать это кратно — в этом весь экономический аргумент.
  • Счётчик противоречий. Должен быть нулём, и любое ненулевое значение обязано быть видно без похода на поиски.

Коротко

  • Проектируйте против уверенной неправоты, а не против «не нашлось». Провал выборки громкий и самокорректирующийся; устаревшая уверенность тиха и накапливается.
  • Наводите гигиену на записи, при живом авторе. Чтение — уже поздно и слишком дорого.
  • Сообщайте о почти-дубликатах вместо слияния. Архивируйте вместо удаления.
  • Типизируйте каждую запись. Состоянию — срок годности или вывод из ground truth.
  • Читать автоматически, писать осознанно. Никогда не хранить то, что уже записано в репозитории или в git.
  • Проставляйте область каждой записи: репо, хост, команда.
  • Заставьте хранилище отчитываться о своём здоровье и считайте противоречия аварией.

Память закрывает то, что вообще не должно было попадать в поиск. Материал, который в поиск попадать обязан, — тема поста про выборку под бюджет токенов; запуск нескольких агентов на одном репозитории без взаимных наступаний — следующая задача в этом ряду. Если хотите такой слой в собственном стеке — это направление AI-разработка.

Связаться

Прямая связь с инженером — Telegram, Email, Calendly или структурированный бриф.

Бесплатный 30-минутный звонок — без обязательств, без агентской воронки.