На данный момент я прохожу 5-дневный интенсив по AI-агентам от Google и параллельно веду собственный конспект. Эта статья представляет собой перевод оригинального материала, выполненный с помощью Gemini и мной. В некоторых местах я немного упростила формулировки или обобщила идеи. Сегодня мы узнаем, как сделать так, чтобы ИИ не просто "отвечал", а "понимал" и "запоминал"? И если вы когда-либо задумывались о том, как научить LLM-агентов вести осмысленные, долгосрочные беседы, эта статья станет вашим проводником в мир сессий и памяти, которые формируют ИИ агентов.
Оригинал статьи тут Context Engineering: Sessions, Memory
Введение
В этом материале мы рассмотрим ключевую роль Сессий (Sessions) и Памяти (Memory) в создании интеллектуальных stateful-агентов на базе LLM. Это поможет разработчикам создавать более мощные, персонализированные и целостные (persistent) AI-системы.
Чтобы Large Language Models (LLM) могли запоминать, обучаться и персонализировать взаимодействие, разработчики должны динамически собирать и управлять информацией в их контекстном окне. Этот процесс известен как Context Engineering (инженерия контекста).
Ключевые концепции, рассматриваемые в этом материале:
Context Engineering (инженерия контекста): Процесс динамической сборки и управления информацией в контекстном окне LLM для создания stateful-агентов, способных поддерживать контекст диалога.
Сессии (Sessions): «Оболочка» для всего диалога с агентом, которая хранит хронологическую историю общения и оперативную (working) память агента.
Память (Memory): Механизм для долговременного хранения данных, который собирает и обобщает ключевую информацию из нескольких сессий. Это обеспечивает непрерывность и персонализацию взаимодействия с LLM-агентом.
Инженерия контекста (Context Engineering)
По своей природе LLM не имеют состояния (stateless). Вне своих обучающих данных их логика и осведомлённость ограничены информацией, предоставленной в «контекстном окне» одного API-вызова. Это создаёт фундаментальную проблему, поскольку AI-агенты должны быть снабжены инструкциями о том, какие действия они могут выполнять, фактическими данными для анализа и информацией из текущего диалога, которая определяет задачу.
Чтобы создавать stateful-агентов (агентов с состоянием), которые могут запоминать, обучаться и персонализировать взаимодействие, разработчики должны формировать этот контекст на каждом шаге диалога. Этот процесс динамической сборки и управления информацией для LLM и называется Context Engineering (инженерия контекста).
Инженерия контекста — это эволюция традиционной инженерии промптов (Prompt Engineering). Инженерия промптов фокусируется на создании оптимальных, зачастую статичных, системных инструкций. В отличие от этого, инженерия контекста работает со всей полезной нагрузкой (payload), динамически создавая промпт, учитывающий состояние (state-aware), на основе данных о пользователе, истории диалога и внешних источниках. Она включает в себя стратегический отбор, обобщение и добавление различных типов информации, чтобы максимизировать релевантность и минимизировать «шум».
Большую часть этого контекста хранят и обрабатывают внешние системы, такие как RAG-базы данных, хранилища сессий и менеджеры памяти. Фреймворк агента должен оркестрировать работу этих систем, чтобы извлекать и собирать контекст в итоговый промпт.
Представьте инженерию контекста как подготовку рабочего места шеф-повара (mise en place) — тот самый важный этап, когда повар собирает и подготавливает все ингредиенты перед началом готовки. Если дать повару только рецепт (промпт), он, возможно, приготовит сносное блюдо из тех случайных ингредиентов, что есть под рукой. Но если вы заранее убедитесь, что у него есть все нужные, качественные ингредиенты, специальные инструменты и чёткое понимание стиля подачи, он сможет стабильно готовить превосходные, индивидуальные блюда.
Цель инженерии контекста — убедиться, что у модели есть ровно столько релевантной информации, сколько нужно для выполнения задачи, — ни больше, ни меньше.
Инженерия контекста управляет сборкой сложной полезной нагрузки (payload), которая может включать в себя разнообразные компоненты:
1. Контекст, направляющий рассуждения
Этот тип контекста определяет фундаментальные шаблоны мышления агента и доступные ему действия, диктуя его поведение.
Системные инструкции (System Instructions): Высокоуровневые директивы, определяющие роль (persona), возможности и ограничения агента.
Описания инструментов (Tool Definitions): Схемы API или функций, которые агент может использовать для взаимодействия с внешним миром.
Примеры для обучения (Few-Shot Examples): Тщательно подобранные примеры, которые направляют логику модели через обучение в контексте (in-context learning).
2. Фактические и доказательные данные
Это основные данные, на основе которых агент строит свои рассуждения. Они включают как ранее известные знания, так и информацию, динамически получаемую для конкретной задачи, и служат «доказательной базой» для ответа агента.
Долгосрочная память (Long-Term Memory): Сохранённые знания о пользователе или теме, собранные за несколько сессий.
Внешние знания (External Knowledge): Информация, полученная из баз данных или документов, часто с использованием Retrieval-Augmented Generation (RAG).
Результаты работы инструментов (Tool Outputs): Данные, возвращённые инструментом.
Результаты работы подагентов (Sub-Agent Outputs): Выводы или результаты, возвращённые специализированными агентами, которым была делегирована конкретная подзадача.
Артефакты (Artifacts): Нетекстовые данные (например, файлы, изображения), связанные с пользователем или сессией.
3. Непосредственная информация из диалога
Этот тип контекста «заземляет» агента в текущем взаимодействии, определяя его непосредственную задачу.
История диалога (Conversation History): Пошаговая запись текущего взаимодействия.
Состояние / «Черновик» (State / Scratchpad): Временная, промежуточная информация или расчёты, которые агент использует в процессе рассуждений.
Запрос пользователя (User's Prompt): Непосредственный запрос, на который нужно ответить.
Динамическое формирование контекста критически важно. Память, например, не статична; её нужно избирательно извлекать и обновлять по мере взаимодействия пользователя с агентом или поступления новых данных. Кроме того, эффективные рассуждения часто опираются на обучение в контексте (in-context learning) — процесс, при котором LLM учится выполнять задачи на основе демонстраций прямо в промпте. Обучение в контексте может быть более эффективным, когда агент использует примеры (few-shot examples), релевантные текущей задаче, а не полагается на жёстко прописанные (hardcoded) шаблоны. Аналогично, внешние знания извлекаются RAG-инструментами на основе непосредственного запроса пользователя.
Одна из самых серьёзных проблем при создании агента, осведомлённого о контексте, — это управление постоянно растущей историей диалога. Теоретически, модели с большими контекстными окнами могут обрабатывать обширные переписки. На практике же, по мере роста контекста, увеличиваются стоимость и задержки (latency). Кроме того, модели могут страдать от «затухания контекста» (context rot) — явления, при котором их способность уделять внимание критически важной информации снижается по мере увеличения объёма контекста.
Context Engineering напрямую решает эту проблему, применяя стратегии для динамического изменения истории — такие как суммаризация, выборочное удаление (pruning) или другие методы сжатия. Это позволяет сохранить жизненно важную информацию, контролируя при этом общее количество токенов, и в конечном итоге приводит к созданию более надёжных и персонализированных AI-систем.
На практике это реализуется как непрерывный цикл в рамках операционной петли агента на каждом шаге (turn) диалога:

Извлечение контекста (Fetch Context): Агент начинает с получения контекста — например, сохранённых данных о пользователе, документов из RAG и истории недавних сообщений. Для динамического извлечения агент использует запрос пользователя и другие метаданные, чтобы определить, какую информацию нужно получить.
Подготовка контекста (Prepare Context): Фреймворк агента динамически формирует полный промпт для вызова LLM. Хотя отдельные API-вызовы могут быть асинхронными, подготовка контекста — это блокирующий процесс, находящийся на критическом пути выполнения (hot-path). Агент не может продолжить работу, пока контекст не будет готов.
Вызов LLM и Инструментов (Invoke LLM and Tools): Агент итеративно вызывает LLM и необходимые инструменты, пока не будет сгенерирован финальный ответ для пользователя. Результаты работы инструментов и модели добавляются в контекст.
Сохранение контекста (Upload Context): Новая информация, собранная за текущий шаг, загружается в постоянное хранилище. Часто это «фоновый» процесс, который позволяет агенту завершить свою работу, пока консолидация памяти или другая постобработка происходят асинхронно.
В основе этого жизненного цикла лежат два фундаментальных компонента: сессии и память. Сессия управляет пошаговым состоянием одного диалога. Память, в свою очередь, обеспечивает механизм долговременного хранения, собирая и обобщая ключевую информацию из нескольких сессий.
Представьте сессию как рабочий стол, который вы используете для конкретного проекта. Пока вы работаете, он завален всеми необходимыми инструментами, заметками и справочными материалами. Всё находится под рукой, но всё это временно и относится только к текущей задаче.
Когда проект закончен, вы не просто запихиваете весь этот беспорядок в шкаф. Вместо этого вы начинаете процесс создания памяти, которая похожа на организованную картотеку. Вы просматриваете материалы на столе, выбрасываете черновики и лишние записи и подшиваете в папки с пометками только самые важные, итоговые документы. Это гарантирует, что картотека останется чистым, надёжным и эффективным источником информации для всех будущих проектов, не захламлённым временным хаосом рабочего стола.
Эта аналогия напрямую отражает то, как работает эффективный агент: сессия служит временным рабочим столом для одного диалога, а память агента — это тщательно организованная картотека, позволяющая ему вспоминать ключевую информацию в ходе будущих взаимодействий.
Опираясь на этот общий обзор инженерии контекста, мы можем теперь перейти к рассмотрению двух ключевых компонентов: сессий и памяти. Начнём с сессий.
Сессии
Фундаментальным элементом инженерии контекста является сессия, которая инкапсулирует непосредственную историю диалога и рабочую память для одного непрерывного разговора. Каждая сессия — это самодостаточная запись, привязанная к конкретному пользователю. Сессия позволяет агенту поддерживать контекст и давать связные ответы в рамках одного диалога. У пользователя может быть несколько сессий, но каждая из них функционирует как отдельный, не связанный с другими журнал конкретного взаимодействия.
Каждая сессия содержит два ключевых компонента: хронологическую историю (события) и рабочую память агента (состояние).
События (Events) — это «строительные блоки» диалога. К распространённым типам событий относятся:
Ввод пользователя (user input): Сообщение от пользователя (текст, аудио, изображение и т.д.).
Ответ агента (agent response): Ответ агента пользователю.
Вызов инструмента (tool call): Решение агента использовать внешний инструмент или API.
Результат работы инструмента (tool output): Данные, возвращённые после вызова инструмента, которые агент использует для продолжения своих рассуждений.
Помимо истории чата, сессия часто включает в себя состояние (state) — структурированную «рабочую память» или «черновик» (scratchpad). Здесь хранятся временные, структурированные данные, относящиеся к текущему диалогу, например, какие товары находятся в корзине.
По мере развития диалога агент будет добавлять в сессию новые события. Кроме того, он может изменять состояние (state) на основе своей внутренней логики.
Структура событий аналогична списку объектов Content, передаваемому в Gemini API, где каждый элемент с role (ролью) и parts (частями) представляет собой один шаг (turn) — или одно Событие — в диалоге.

Рабочая среда выполнения (execution environment) агента в продакшене, как правило, является stateless (не сохраняющей состояние). Это означает, что она не удерживает никакой информации после завершения запроса. Следовательно, история диалога должна сохраняться в постоянное хранилище (persistent storage), чтобы обеспечить непрерывность пользовательского опыта.
Хотя хранение в оперативной памяти (in-memory) подходит для разработки, в рабочих приложениях (production applications) для надёжного хранения и управления сессиями следует использовать надёжные базы данных. Например, историю диалога можно хранить в управляемых решениях, таких как Agent Engine Sessions³.
Различия между фреймворками и моделями
Хотя основные идеи схожи, разные фреймворки для создания агентов реализуют сессии, события и состояние по-своему.
Фреймворки отвечают за поддержание истории диалога и состояния для LLM, формирование запросов к LLM с использованием этого контекста, а также за обработку (parsing) и сохранение ответа от LLM. Фреймворк агента действует как универсальный переводчик между вашим кодом и LLM.
Пока вы, как разработчик, работаете с едиными внутренними структурами данных фреймворка на каждом шаге диалога, сам фреймворк выполняет критически важную задачу: преобразует эти структуры в тот конкретный формат, который требует LLM.
Эта абстракция очень важна, поскольку она отделяет логику вашего агента от конкретной LLM, которую вы используете, предотвращая зависимость от одного поставщика (vendor lock-in).

В конечном счёте, цель — сформировать «запрос» (request), который LLM сможет понять. Для моделей Gemini от Google это List[Content] (список объектов Content). Каждый объект Content — это простая, словарно-подобная структура с двумя ключами: role, который определяет, кто говорит ("user" или "model"), и parts, который содержит непосредственно само сообщение (текст, изображения, вызовы инструментов и т.д.).
Фреймворк автоматически выполняет сопоставление (mapping) данных из своего внутреннего объекта (например, Event в ADK) с соответствующими полями role и parts в объекте Content перед тем, как сделать API-вызов.
По сути, фреймворк предоставляет разработчику стабильный внутренний API, в то же время «под капотом» управляя сложными и разнообразными внешними API различных LLM
ADK использует явный объект Session, который содержит список объектов Event (событий) и отдельный объект state (состояние). Session здесь похож на картотечный шкаф: одна папка для истории диалога (события), другая — для рабочей памяти (состояние).
В LangGraph нет формального объекта «сессия». Вместо этого, состояние (state) и есть сессия. Этот всеобъемлющий объект state хранит и историю диалога (в виде списка объектов Message), и все остальные рабочие данные. В отличие от традиционной сессии, которая работает как лог, куда данные только добавляются (append-only), состояние в LangGraph является изменяемым (mutable). Его можно трансформировать, а такие стратегии, как сжатие истории (history compaction), могут изменять саму запись. Это полезно для управления длинными диалогами и лимитами токенов.
Сессии для мультиагентных систем
В мультиагентной системе несколько агентов работают совместно. Каждый агент фокусируется на своей небольшой, узкоспециализированной задаче. Чтобы эти агенты могли эффективно взаимодействовать, они должны обмениваться информацией.
Как показано на диаграмме ниже, архитектура системы определяет паттерны коммуникации, которые они используют для обмена информацией. Центральным компонентом этой архитектуры является то, как система обрабатывает историю сессии — постоянный (persistent) лог всех взаимодействий.

Прежде чем рассматривать архитектурные паттерны для управления этой историей, крайне важно провести различие между ней и контекстом, отправляемым в LLM.
Представьте историю сессии как полную, неотредактированную стенограмму всего диалога.
Контекст же, с другой стороны, — это тщательно подготовленная порция информации (payload), отправляемая в LLM для одного-единственного шага (turn) в диалоге. Агент может формировать этот контекст, выбирая из истории лишь релевантный фрагмент или добавляя специальное форматирование, например, направляющую преамбулу, чтобы скорректировать ответ модели.
Этот раздел посвящён тому, какая информация передаётся между агентами, а не тому, какой контекст обязательно отправляется в LLM.
Фреймворки для агентов обрабатывают историю сессий в мультиагентных системах, используя один из двух основных подходов: общая, единая история, в которую все агенты вносят свой вклад, или отдельные, индивидуальные истории, где каждый агент ведёт свой собственный лог⁴. Выбор между этими двумя паттернами зависит от характера задачи и желаемого стиля взаимодействия между агентами.
Общая, единая история (Shared, Unified History)
В модели с общей, единой историей все агенты в системе читают и записывают все события в один и тот же лог диалога. Сообщение каждого агента, вызов инструмента и результат наблюдения добавляются в один центральный лог в хронологическом порядке.
Этот подход лучше всего подходит для тесно связанных, совместных задач, требующих единого источника истины (single source of truth), например, для многоэтапного процесса решения проблемы, где результат работы одного агента является прямыми входными данными для следующего.
Даже при наличии общей истории подагент может предварительно обработать лог, прежде чем передать его в LLM. Например, он может отфильтровать его, оставив только подмножество релевантных событий, или добавить метки, чтобы указать, какой агент сгенерировал каждое событие.
Если вы используете в ADK делегирование на основе LLM для передачи задач подагентам, все промежуточные события подагента будут записаны в ту же сессию, что и у корневого агента⁵.


Раздельные, индивидуальные истории (Separate, Individual Histories)
В модели с раздельными, индивидуальными историями каждый агент ведёт свой собственный, приватный лог диалога и функционирует как «чёрный ящик» для других агентов. Все внутренние процессы — такие как промежуточные рассуждения, использование инструментов и шаги логических выводов — остаются в приватном логе агента и не видны другим.
Коммуникация происходит только через явные сообщения, в которых агент делится своим конечным результатом, а не процессом его получения.
Такое взаимодействие обычно реализуется либо через паттерн «Агент как инструмент» (Agent-as-a-tool), либо с использованием протокола Agent-to-Agent (A2A).
В подходе «Агент как инструмент» один агент вызывает другого так, как если бы это был обычный инструмент, передавая ему входные данные и получая итоговый, самодостаточный результат⁶.
С помощью протокола A2A агенты используют структурированный протокол для прямого обмена сообщениями⁷.
Мы подробнее рассмотрим протокол A2A на следующем занятии.
Взаимодействие(Interoperability) между различными фреймворками для агентов

Использование фреймворком внутреннего представления данных создаёт критический архитектурный компромисс для мультиагентных систем: та самая абстракция, которая отделяет агента от LLM, также изолирует его от агентов, использующих другие фреймворки.
Эта изоляция закрепляется на уровне хранения данных (persistence layer). Модель хранения Сессии обычно напрямую связывает схему базы данных с внутренними объектами фреймворка, создавая жёсткую, плохо переносимую запись диалога. В результате агент, созданный с помощью LangGraph, не может напрямую интерпретировать отдельные объекты Session и Event, сохранённые агентом на базе ADK, что делает бесшовную передачу задач невозможной.
Одним из новых архитектурных паттернов для координации взаимодействия между такими изолированными агентами является протокол Agent-to-Agent (A2A)⁸. Хотя этот паттерн позволяет агентам обмениваться сообщениями, он не решает основную проблему — обмен полным/богатым, контекстным состоянием. История диалога каждого агента закодирована во внутренней схеме его фреймворка. Вследствие этого, любое A2A-сообщение, содержащее события сессии, требует наличия слоя трансляции, чтобы быть полезным.
Более надёжный архитектурный паттерн для обеспечения совместимости (interoperability) предполагает вынесение общих знаний в независимый от фреймворка слой данных, такой как Память (Memory).
В отличие от хранилища Сессий, которое сохраняет «сырые», специфичные для фреймворка объекты вроде Events и Messages, слой памяти предназначен для хранения обработанной, канонической информации. Ключевые сведения — такие как краткие выжимки (summaries), извлечённые сущности и факты — извлекаются из диалога и обычно хранятся в виде строк или словарей. Структуры данных слоя памяти не привязаны к внутреннему представлению данных какого-либо одного фреймворка, что позволяет ему служить универсальным, общим слоем данных.
Этот паттерн позволяет гетерогенным (разнородным) агентам достичь подлинного совместного интеллекта, разделяя общий когнитивный ресурс без необходимости в кастомных трансляторах.
Аспекты работы с сессиями в продакшене
При переносе агента в рабочую среду (production environment), его система управления сессиями должна эволюционировать от простого лога до надёжного сервиса корпоративного уровня. Ключевые аспекты здесь делятся на три критически важные области: безопасность и конфиденциальность, целостность данных и производительность. Управляемые хранилища сессий, такие как Agent Engine Sessions, специально разработаны для удовлетворения этих производственных требований.
Безопасность и конфиденциальность
Защита конфиденциальной информации, содержащейся в сессии, — это необсуждаемое требование.
Строгая изоляция — самый важный принцип безопасности. Сессия принадлежит одному пользователю, и система должна обеспечивать строгую изоляцию, чтобы один пользователь никогда не смог получить доступ к данным сессии другого (например, с помощью ACL). Каждый запрос к хранилищу сессий должен быть аутентифицирован и авторизован в соответствии с владельцем сессии.
Лучшая практика для обработки персональных данных (PII) — удалять (redact) их до того, как данные сессии будут записаны в хранилище. Это фундаментальная мера безопасности, которая значительно снижает риск и «радиус поражения» (blast radius) в случае потенциальной утечки данных. Обеспечивая, чтобы конфиденциальные данные никогда не сохранялись (например, с помощью таких инструментов, как Model Armor⁹), вы упрощаете соблюдение нормативных требований по защите данных, таких как GDPR и CCPA, и укрепляете доверие пользователей.
Целостность данных и управление жизненным циклом
Рабочая система требует чётких правил хранения и поддержки данных сессий с течением времени. Сессии не должны храниться вечно. Вы можете реализовать политику Time-to-Live (TTL) для автоматического удаления неактивных сессий, чтобы управлять затратами на хранение и снижать накладные расходы на управление данными. Это требует чёткой политики хранения данных, которая определяет, как долго сессии должны храниться перед архивацией или окончательным удалением.
Кроме того, система должна гарантировать, что операции добавляются в историю сессии в детерминированном (строго определённом) порядке. Поддержание правильной хронологической последовательности событий является основой целостности лога диалога.
Производительность и масштабируемость
Данные сессии находятся на «критическом пути» (hot path) каждого взаимодействия с пользователем, что делает их производительность первостепенной задачей. Чтение и запись истории сессии должны быть чрезвычайно быстрыми, чтобы обеспечить отзывчивость пользовательского интерфейса. Среды выполнения (runtimes) агентов, как правило, являются stateless (не сохраняют состояние), поэтому вся история сессии извлекается из центральной базы данных в начале каждого шага (turn) диалога, что влечёт за собой задержки, связанные с передачей данных по сети.
Чтобы уменьшить задержки (latency), крайне важно сократить объём передаваемых данных. Ключевая оптимизация — это фильтрация или сжатие истории сессии перед её отправкой агенту. Например, можно удалить старые, нерелевантные результаты вызовов функций, которые больше не нужны для текущего состояния диалога.
В следующем разделе подробно рассматриваются несколько стратегий сжатия истории для эффективного управления диалогами с длинным контекстом.
Управление диалогами с длинным контекстом: компромиссы и оптимизации
В упрощённой архитектуре сессия представляет собой неизменяемый (immutable) лог диалога между пользователем и агентом. Однако по мере его роста увеличивается и количество используемых токенов. Современные LLM могут обрабатывать длинные контексты, но существуют ограничения, особенно для приложений, чувствительных к задержкам (latency)¹⁰:
Лимиты контекстного окна: У каждой LLM есть максимальный объём текста (контекстное окно), который она может обработать за один раз. Если история диалога превысит этот лимит, API-вызов завершится ошибкой.
Стоимость API ($): Большинство LLM-провайдеров взимают плату в зависимости от количества отправленных и полученных токенов. Более короткая история означает меньше токенов и ниже стоимость каждого шага (turn) диалога.
Задержка (скорость): Отправка большего объёма текста в модель требует больше времени на обработку, что приводит к увеличению времени ответа для пользователя. Сжатие (compaction) помогает агенту оставаться быстрым и отзывчивым.
Качество: С увеличением количества токенов производительность может ухудшаться из-за дополнительного «шума» в контексте и авторегрессионных ошибок.
Управление длинным диалогом с агентом можно сравнить с тем, как опытный путешественник собирает чемодан для долгой поездки. Чемодан — это ограниченное контекстное окно агента, а одежда и вещи — это фрагменты информации из диалога.
Если вы просто попытаетесь впихнуть в чемодан всё подряд, он станет слишком тяжёлым и неупорядоченным, и в нём будет трудно быстро найти то, что вам нужно — точно так же, как перегруженное контекстное окно увеличивает затраты на обработку и замедляет время ответа. С другой стороны, если вы возьмёте слишком мало, вы рискуете оставить дома важные вещи, такие как паспорт или тёплую куртку, поставив под угрозу всю поездку — так же, как агент может потерять критически важный контекст, что приведёт к нерелевантным или неверным ответам.
И путешественник, и агент действуют в рамках схожего ограничения: успех зависит не от того, сколько вы можете унести, а от того, чтобы взять с собой только то, что действительно нужно.
Стратегии сжатия (Compaction strategies) сокращают длинные истории диалогов, уплотняя их, чтобы они помещались в контекстное окно модели, снижая затраты на API и задержки. По мере удлинения диалога история, отправляемая модели на каждом шаге, может стать слишком большой. Стратегии сжатия решают эту проблему, интеллектуально «подрезая» историю и стараясь при этом сохранить наиболее важный контекст.
Итак, как понять, какую информацию можно выбросить из Сессии, не потеряв ничего ценного? Стратегии варьируются от простого усечения до сложных методов сжатия.
Сохранять последние N шагов (Keep the last N turns): Это самая простая стратегия. Агент хранит только N самых последних шагов (turns) диалога (так называемое «скользящее окно»(a “sliding window”)) и отбрасывает всё, что было раньше.
Усечение по токенам (Token-Based Truncation): Перед отправкой истории в модель агент подсчитывает количество токенов в сообщениях, начиная с самого последнего и двигаясь в обратном порядке. Он включает в контекст столько сообщений, сколько возможно, не превышая заранее определённый лимит токенов (например, 4000). Всё, что было раньше, просто отсекается.
Рекурсивная суммаризация (Recursive Summarization): Более старые части диалога заменяются на краткую выжимку, сгенерированную AI. По мере роста диалога агент периодически использует ещё один вызов LLM, чтобы суммировать самые старые сообщения. Эта краткая выжимка затем используется как сжатая форма истории, часто добавляемая в начало перед более свежими, дословными сообщениями.
Например, в ADK вы можете сохранять последние N шагов, используя встроенный плагин для вашего ADK-приложения, чтобы ограничить контекст, отправляемый в модель. Важно отметить, что это не изменяет исторические события, хранящиеся в вашем хранилище сессий:

Учитывая, что сложные стратегии сжатия направлены на снижение затрат и задержек, критически важно выполнять ресурсоёмкие операции (такие как рекурсивная суммаризация) асинхронно в фоновом режиме и сохранять (asynchronously
in the background and persist the results) результаты. «Фоновый режим» гарантирует, что клиент не будет ждать, а «сохранение» — что дорогостоящие вычисления не будут повторяться без необходимости.
Часто именно менеджер памяти агента отвечает и за генерацию, и за сохранение этих рекурсивных сводок. Агент также должен вести учёт того, какие именно события были включены в сжатую сводку; это предотвращает ненужную отправку в LLM оригинальных, более подробных событий.
Кроме того, агент должен решать, когда необходимо сжатие. Механизм запуска (trigger) обычно относится к одной из нескольких категорий:
Триггеры на основе количества (например, порог по размеру токенов или числу шагов): Сжатие запускается, как только диалог превышает определённый порог. Этот подход часто является «достаточно хорошим» для управления длиной контекста.
Триггеры на основе времени: Сжатие запускается не из-за размера диалога, а из-за отсутствия активности. Если пользователь прекращает взаимодействовать на определённый период (например, 15 или 30 минут), система может запустить задачу сжатия в фоновом режиме.
Триггеры на основе событий (например, семантическое завершение/завершение задачи): Агент решает запустить сжатие, когда обнаруживает, что определённая задача, подцель или тема разговора завершена.
Например, вы можете использовать EventsCompactionConfig в ADK, чтобы запустить суммаризацию на основе LLM после заданного количества шагов (turns):

Генерация памяти — это широкое понятие, означающее извлечение постоянных (persistent) знаний из подробного и «зашумлённого» источника данных. В этом разделе мы рассмотрели основной пример извлечения информации из истории диалога — сжатие сессии (session compaction). Сжатие, по сути, «дистиллирует» дословную стенограмму всего разговора, извлекая ключевые факты и краткие выжимки и отбрасывая при этом разговорный «наполнитель».
Опираясь на концепцию сжатия, в следующем разделе мы рассмотрим генерацию и управление памятью в более широком смысле. Мы обсудим различные способы, которыми «воспоминания» (memories) могут создаваться, храниться и извлекаться для формирования долгосрочных знаний агента.
Память (Memory)
Память и Сессии тесно взаимосвязаны: сессии служат основным источником данных для формирования записей в памяти, а память, в свою очередь, является ключевой стратегией для управления объёмом сессии.
Память — это, по сути, концентрированная выжимка ключевой информации, извлечённой из диалога или источника данных. Это сжатое представление, которое сохраняет важный контекст, делая его полезным для будущих взаимодействий. Как правило, данные в памяти сохраняются между сессиями, чтобы обеспечить непрерывный и персонализированный опыт.
«Менеджер памяти», выступающий как специализированный, независимый (decoupled) сервис, закладывает основу для совместимости (interoperability) мультиагентных систем. Менеджеры памяти часто используют независимые от фреймворка структуры данных, такие как простые строки и словари. Это позволяет агентам, созданным на разных фреймворках, подключаться к единому хранилищу памяти, создавая общую базу знаний, которую может использовать любой подключённый агент.
Примечание: некоторые фреймворки могут называть Сессии или дословную историю диалога «краткосрочной памятью». В этом материале под памятью (memories) понимается именно извлечённая информация, а не «сырой» пошаговый диалог.
Хранение и извлечение данных из памяти критически важно для создания продвинутых и интеллектуальных агентов. Надёжная система памяти превращает простого чат-бота в по-настоящему интеллектуального агента, наделяя его несколькими ключевыми возможностями:
Персонализация: Самый частый сценарий использования — запоминание предпочтений пользователя, фактов и прошлых взаимодействий для адаптации будущих ответов. Например, если агент помнит любимую спортивную команду пользователя или предпочитаемое им место в самолёте, это делает взаимодействие более полезным и личным.
Управление контекстным окном: По мере удлинения диалогов их полная история может превысить лимит контекстного окна LLM. Системы памяти могут сжимать эту историю, создавая краткие выжимки или извлекая ключевые факты. Это позволяет сохранить контекст, не отправляя тысячи токенов на каждом шаге, что снижает и стоимость, и задержки (latency).
Анализ данных и получение инсайтов: Анализируя сохранённые данные по многим пользователям (в агрегированном, анонимном виде), можно извлекать ценные сведения из информационного шума. Например, чат-бот в ритейле может обнаружить, что многие пользователи спрашивают о правилах возврата конкретного товара, сигнализируя о потенциальной проблеме.
Самосовершенствование и адаптация агента: Агент учится на предыдущих запусках, создавая процедурные знания (procedural memories) о собственной производительности — он записывает, какие стратегии, инструменты или логические цепочки привели к успешным результатам. Это позволяет агенту со временем формировать базу эффективных решений, адаптируясь и совершенствуя свои навыки решения задач.
Создание, хранение и использование памяти в AI-системе — это совместный процесс. У каждого компонента в общей архитектуре (stack) — от конечного пользователя до кода разработчика — своя, чётко определённая роль.
Пользователь: Предоставляет исходные «сырые» данные для памяти. В некоторых системах пользователи могут предоставлять данные напрямую (например, через форму).
-
Агент (Логика разработчика): Определяет, что и когда запоминать, управляя вызовами к менеджеру памяти.
В простых архитектурах разработчик может реализовать логику так, что память всегда извлекается и её создание всегда инициируется.
В более сложных архитектурах разработчик может реализовать память как инструмент (memory-as-a-tool), где агент (с помощью LLM) сам решает, когда следует извлекать или генерировать данные для памяти.
Фреймворк агента (например, ADK, LangGraph): Предоставляет структуру и инструменты для взаимодействия с памятью. Фреймворк выступает в роли связующей инфраструктуры (plumbing). Он определяет, как логика разработчика может получить доступ к истории диалога и взаимодействовать с менеджером памяти, но сам не управляет долговременным хранилищем. (defines how the developer's
logic can access conversation history and interact with the memory manager, but
it doesn't manage the long-term storage itself.) Он также определяет, как извлечённые из памяти данные добавляются в контекстное окно.Хранилище сессий (например, Agent Engine Sessions, Spanner, Redis): Хранит пошаговый диалог Сессии. Необработанный диалог используется менеджером памяти для генерации записей в памяти.
-
Менеджер памяти (например, Agent Engine Memory Bank, Mem0, Zep): Отвечает за хранение, извлечение и сжатие данных памяти. Механизмы хранения и извлечения зависят от используемого провайдера. Это специализированный сервис, который берёт потенциальные «воспоминания», определённые агентом, и управляет всем их жизненным циклом:
Извлечение (Extraction): Извлекает ключевую информацию из исходных данных.
Консолидация (Consolidation): Устраняет дубликаты и объединяет связанные данные.
Хранение (Storage): Обеспечивает сохранение данных в постоянных базах данных.
Получение (Retrieval): Извлекает релевантные данные для предоставления контекста в новых взаимодействиях.

Такое разделение обязанностей позволяет разработчику сосредоточиться на уникальной логике агента, не создавая с нуля сложную базовую инфраструктуру для хранения и управления памятью.
Важно понимать, что менеджер памяти — это активная система, а не просто пассивная векторная база данных. Хотя он использует поиск по сходству (similarity search) для извлечения данных, его основная ценность заключается в способности интеллектуально извлекать, консолидировать и курировать записи в памяти с течением времени. Управляемые сервисы памяти, такие как Agent Engine Memory Bank, берут на себя весь жизненный цикл генерации и хранения данных, освобождая вас, чтобы вы могли сосредоточиться на основной логике вашего агента.
Именно благодаря функции извлечения данных память часто сравнивают с другим ключевым архитектурным паттерном: Retrieval-Augmented Generation (RAG). Однако они построены на разных архитектурных принципах: RAG работает со статичными, внешними данными, в то время как Memory курирует динамический, специфичный для пользователя контекст.
Они выполняют две разные, но взаимодополняющие роли: RAG делает агента экспертом по фактам, а Memory — экспертом по пользователю.
В следующей таблице представлены их основные различия:

Чтобы лучше понять разницу, представьте, что RAG — это научный библиотекарь агента, а менеджер памяти — его личный помощник.
Научный библиотекарь (RAG) работает в огромной публичной библиотеке, полной энциклопедий, учебников и официальных документов. Когда агенту нужен проверенный факт — например, технические характеристики продукта или историческая дата — он обращается к библиотекарю. Библиотекарь извлекает информацию из этой статичной, общей и авторитетной базы знаний, чтобы предоставить достоверные, основанные на фактах ответы. Библиотекарь — эксперт по фактам о мире, но он ничего не знает лично о пользователе, который задаёт вопрос.
Напротив, личный помощник (память) всегда сопровождает агента и ведёт личный блокнот, записывая в него детали каждого взаимодействия с конкретным пользователем. Этот блокнот постоянно обновляется, строго конфиденциален и содержит личные предпочтения, историю прошлых диалогов и меняющиеся цели. Когда агенту нужно вспомнить любимую спортивную команду пользователя или контекст обсуждения проекта на прошлой неделе, он обращается к помощнику. Сильная сторона помощника — не знание фактов о мире, а глубокое понимание самого пользователя.
В конечном итоге, по-настоястоящему интеллектуальному агенту нужно и то, и другое. RAG даёт ему экспертные знания о мире, а память — экспертное понимание пользователя, которому он помогает.
В следующем разделе мы детально разберём концепцию памяти, рассмотрев её ключевые компоненты: типы хранимой информации, способы её организации, механизмы хранения и создания, стратегическое определение её области применения и обработку мультимодальных и текстовых данных.
Типы памяти
Память агента можно классифицировать по тому, как информация хранится и как она была получена. Эти различные типы памяти работают вместе, чтобы создать богатое, контекстное понимание пользователя и его потребностей. Для всех типов памяти действует правило: память является описательной, а не предсказательной.
«Единица памяти» (memory) — это атомарный/базовый/неделимый/самодостаточный фрагмент контекста, который возвращается менеджером памяти и используется агентом. Хотя точная схема может варьироваться, одна единица памяти обычно состоит из двух основных компонентов: содержимого (content) и метаданных (metadata).
Содержимое (Content) — это суть «воспоминания», извлечённая из исходных данных (например, из необработанного диалога сессии). Крайне важно, что содержимое проектируется так, чтобы быть независимым от фреймворка, используя простые структуры данных, которые любой агент может легко обработать. Содержимое может быть как структурированным, так и неструктурированным.
Структурированная память включает информацию, обычно хранящуюся в универсальных форматах, таких как словарь или JSON. Её схема, как правило, определяется разработчиком, а не конкретным фреймворком. Например: {"seat_preference": "Window"}.
Неструктурированная память — это описания на естественном языке, которые отражают суть более длительного взаимодействия, события или темы. Например: «Пользователь предпочитает место у окна».
Метаданные (Metadata) предоставляют контекст о самой записи в памяти и обычно хранятся в виде простых строк. Они могут включать уникальный идентификатор записи, идентификаторы «владельца» записи, а также метки, описывающие содержимое или источник данных.
Типы информации
Помимо базовой структуры, записи в памяти можно классифицировать по фундаментальному типу знаний, которые они представляют. Это различие, заимствованное из когнитивной науки¹¹, имеет решающее значение для понимания того, как агент использует память, и делит её на две основные функциональные категории: декларативная память («знать что») и процедурная память («знать как»). (derived from
cognitive science: declarative memories (“knowing what”) and procedural memories
(“knowing how”).)
Декларативная память (Declarative memory)
Это знания агента о фактах, цифрах и событиях. Это вся информация, которую агент может явно сформулировать или «декларировать». Если запись в памяти является ответом на вопрос «что?», — это декларативная память. Эта категория охватывает как общие знания о мире (семантические), так и конкретные факты о пользователе (сущностные/эпизодические).
Процедурная память (Procedural memory)
Это знания агента о навыках и последовательностях действий (workflows). Она направляет действия агента, неявно демонстрируя, как правильно выполнить задачу. Если запись в памяти помогает ответить на вопрос «как?» — например, какая правильная последовательность вызовов инструментов для бронирования поездки, — это процедурная память.
Паттерны организации памяти
После того как запись в памяти создана, следующий вопрос — как её организовать. Менеджеры памяти обычно используют один или несколько из следующих паттернов: Коллекции (Collections)¹², Структурированный профиль пользователя (Structured User Profile) или «Скользящая сводка» (Rolling Summary). Эти паттерны определяют, как отдельные записи в памяти соотносятся друг с другом и с пользователем.
Коллекции (Collections)¹³: Этот паттерн организует контент в виде множества самодостаточных записей на естественном языке для одного пользователя. Каждая запись — это отдельное событие, краткая выжимка или наблюдение, хотя в коллекции может быть несколько записей по одной общей теме. Коллекции позволяют хранить и искать информацию в большом, менее структурированном пуле данных, связанных с конкретными целями или темами.
Структурированный профиль пользователя (Structured User Profile): Этот паттерн организует записи в виде набора ключевых фактов о пользователе, подобно карточке контакта, которая постоянно обновляется новой, стабильной информацией. Он предназначен для быстрого поиска важной фактической информации, такой как имена, предпочтения и детали учётной записи.
«Скользящая сводка» (Rolling Summary): В отличие от профиля, этот паттерн объединяет всю информацию в единую, постоянно развивающуюся запись, которая представляет собой сводку на естественном языке обо всём взаимодействии пользователя и агента. Вместо создания новых, отдельных записей, менеджер непрерывно обновляет этот один «мастер-документ». Этот паттерн часто используется для сжатия длинных Сессий, сохраняя жизненно важную информацию при управлении общим количеством токенов.
Архитектуры хранения
Кроме того, выбор архитектуры хранения — это критически важное решение, которое определяет, насколько быстро и интеллектуально агент сможет извлекать данные из памяти. Выбор архитектуры определяет, в чём агент будет преуспевать: в поиске концептуально схожих идей, в понимании структурированных взаимосвязей или и в том, и в другом.
Записи в памяти обычно хранятся в векторных базах данных (vector databases) и/или графах знаний (knowledge graphs).
Векторные базы данных помогают находить записи, концептуально схожие с запросом.
Графы знаний хранят записи в виде сети сущностей и их взаимосвязей.
Векторные базы данных — самый распространённый подход, позволяющий выполнять поиск на основе семантического сходства, а не точных ключевых слов. Записи в памяти преобразуются в векторные представления (embedding vectors), и база данных находит наиболее близкие по смыслу совпадения с запросом пользователя. Этот метод отлично подходит для извлечения неструктурированных, естественно-языковых записей, где ключевую роль играют контекст и значение (т.е. “atomic facts”. базовые факты/элементарные).
Графы знаний используются для хранения записей в виде сети сущностей (узлов) и их взаимосвязей (рёбер). Извлечение данных включает в себя обход этого графа для поиска прямых и косвенных связей, что позволяет агенту делать выводы о том, как связаны между собой различные факты. Этот метод идеален для структурированных, реляционных запросов и понимания сложных связей внутри данных (т.е. «триплеты знаний»¹⁵).
Можно также объединить оба метода в гибридный подход, обогатив структурированные сущности графа знаний векторными представлениями. Это позволяет системе выполнять одновременно и реляционный, и семантический поиск. Такой подход сочетает структурированные рассуждения графа с тонким концептуальным поиском векторной базы данных, предлагая лучшее из обоих миров.
Механизмы создания
Мы также можем классифицировать память по тому, как она была создана, включая способ получения информации.
Явные воспоминания (Explicit memories) создаются, когда пользователь даёт агенту прямую команду что-то запомнить (например, «Запомни, что моя годовщина — 26 октября»).
Неявные воспоминания (Implicit memories), напротив, создаются, когда агент сам делает вывод и извлекает информацию из диалога без прямой команды (например, «На следующей неделе у меня годовщина. Можешь помочь мне найти подарок для моей второй половинки?»).
Память также можно различать по тому, где находится логика её извлечения — внутри (internal) фреймворка агента или снаружи (external).
Внутренняя память (Internal memory) относится к управлению памятью, встроенному непосредственно во фреймворк агента. Это удобно для быстрого старта, но часто в таких решениях отсутствуют продвинутые функции. Внутренняя память может использовать внешнее хранилище, но сам механизм генерации записей находится внутри агента.
Внешняя память (External Memory) предполагает использование отдельного, специализированного сервиса, предназначенного для управления памятью (например, Agent Engine Memory Bank, Mem0, Zep). Фреймворк агента делает API-вызовы к этому внешнему сервису для хранения, извлечения и обработки данных. Такой подход предоставляет более сложные функции, такие как семантический поиск, извлечение сущностей и автоматическая суммаризация, перекладывая сложную задачу управления памятью на специально созданный для этого инструмент.
Область видимости памяти (Memory scope)
Вам также необходимо определить, кого или что описывает память. Это влияет на то, какую сущность (например, пользователя, сессию или приложение) вы используете для агрегации и извлечения данных из памяти.
Уровень пользователя (User-Level scope): Это самая распространённая реализация, предназначенная для создания непрерывного, персонализированного опыта для каждого отдельного человека. Например: «Пользователь предпочитает место в середине ряда». Данные привязаны к конкретному user ID и сохраняются между всеми его сессиями, что позволяет агенту формировать долгосрочное понимание его предпочтений и истории.
Уровень сессии (Session-Level scope): Этот уровень предназначен для сжатия длинных диалогов. Например: «Пользователь ищет билеты из Нью-Йорка в Париж на даты с 7 по 14 ноября 2025 года. Он предпочитает прямые рейсы и место в середине ряда». Здесь создаётся постоянная запись с ключевыми выводами из одной сессии, что позволяет агенту заменить подробную, «тяжёлую» по токенам стенограмму на краткий набор фактов. Крайне важно, что эта память отличается от «сырого» лога сессии; она содержит только обработанные выводы из диалога, а не сам диалог, и её контекст изолирован в рамках этой конкретной сессии.
Уровень приложения (Application-level scope) (или глобальный контекст): Это данные, доступные всем пользователям приложения. Например: «Кодовое название XYZ относится к проекту...». Эта область видимости используется для предоставления общего контекста, распространения общесистемной информации или формирования базового уровня общих знаний. Распространённый сценарий использования памяти на уровне приложения — это процедурная память, которая предоставляет агенту инструкции «как делать». Такие записи обычно предназначены для улучшения логики агента для всех пользователей. Критически важно, чтобы эти данные были очищены от любой конфиденциальной информации, чтобы предотвратить утечки данных между пользователями.
Мультимодальная память (Multimodal memory)
«Мультимодальная память» — это ключевая концепция, описывающая, как агент обрабатывает нетекстовую информацию, такую как изображения, видео и аудио. Здесь важно различать данные, из которых извлекается память (источник), и данные, в виде которых она хранится (содержимое).
Память из мультимодального источника
Это наиболее распространённая реализация. Агент может обрабатывать различные типы данных — текст, изображения, аудио, — но создаваемая им запись в памяти представляет собой текстовый вывод, извлечённый из этого источника.
Например, агент может обработать голосовую заметку пользователя для создания «воспоминаний». Он не хранит сам аудиофайл; вместо этого он расшифровывает аудио и создаёт текстовую запись, например: «Пользователь выразил недовольство недавней задержкой доставки».
Память с мультимодальным содержимым
Это более продвинутый подход, при котором сама запись в памяти содержит нетекстовые медиафайлы. Агент не просто описывает контент, а хранит его напрямую.
Например, пользователь может загрузить изображение и сказать: «Запомни этот дизайн для нашего логотипа». Агент создаёт запись в памяти, которая напрямую содержит файл изображения, связанный с запросом пользователя.
Большинство современных менеджеров памяти сосредоточены на обработке мультимодальных источников с созданием текстового содержимого. Это связано с тем, что генерация и извлечение неструктурированных двоичных данных, таких как изображения или аудио, для конкретной записи в памяти требует специализированных моделей, алгоритмов и инфраструктуры. Гораздо проще преобразовать все входные данные в единый, удобный для поиска формат: текст.
Например, вы можете генерировать память из мультимодальных входных данных¹⁶, используя Agent Engine Memory Bank. Выходные данные будут представлять собой текстовые выводы, извлечённые из контента:


В следующем разделе мы рассмотрим механику генерации памяти, подробно описав два ключевых этапа: извлечение новой информации из исходных данных и её последующее объединение с уже существующим корпусом памяти.
Генерация памяти: извлечение и объединение
Генерация памяти — это процесс, который автономно преобразует «сырые» данные из диалога в структурированные, осмысленные выводы. Представьте это как ETL-конвейер (Extract, Transform, Load), управляемый LLM и предназначенный для извлечения и сжатия данных для памяти.
Именно этот ETL-конвейер отличает менеджеры памяти от RAG-систем и традиционных баз данных. Вместо того чтобы требовать от разработчиков вручную прописывать операции с базой данных, менеджер памяти использует LLM, чтобы решать, когда добавлять, обновлять или объединять записи.
Эта автоматизация — ключевое преимущество менеджера памяти. Он абстрагирует (скрывает) всю сложность, связанную с управлением содержимым базы данных, выстраиванием цепочек LLM-вызовов и развёртыванием фоновых сервисов для обработки данных.

Хотя конкретные алгоритмы различаются в зависимости от платформы (например, Agent Engine Memory Bank, Mem0, Zep), высокоуровневый процесс генерации памяти обычно проходит следующие четыре этапа:
Приём данных (Ingestion): Процесс начинается, когда клиент предоставляет менеджеру памяти источник «сырых» данных, обычно — историю диалога.
Извлечение и фильтрация (Extraction & Filtering): Менеджер памяти использует LLM для извлечения значимого контента из исходных данных. Ключевой момент в том, что эта LLM извлекает не всё подряд; она фиксирует только ту информацию, которая соответствует заранее определённым темам (topic definition). Если в полученных данных нет информации, соответствующей этим темам, запись в памяти не создаётся.
-
Объединение (Consolidation): Это самый сложный этап, на котором менеджер памяти разрешает конфликты и устраняет дубликаты. Он выполняет процесс «саморедактирования», используя LLM для сравнения новой извлечённой информации с уже существующими записями. Чтобы база знаний пользователя оставалась целостной, точной и развивалась со временем на основе новой информации, менеджер может принять решение:
Объединить новую информацию с существующей записью.
Удалить существующую запись, если она стала неактуальной.
Создать совершенно новую запись, если тема новая.
Хранение (Storage): Наконец, новая или обновлённая запись сохраняется (persists) в надёжный слой хранения (to a durable storage layer) (например, в векторную базу данных или граф знаний), чтобы её можно было извлечь в будущих взаимодействиях.
Управляемые менеджеры памяти, такие как Agent Engine Memory Bank, полностью автоматизируют этот конвейер. Они предоставляют единую, целостную систему для превращения «разговорного шума» в структурированные знания, позволяя разработчикам сосредоточиться на логике агента, а не на создании и поддержке базовой инфраструктуры данных.
Например, для запуска генерации памяти с помощью Memory Bank требуется всего лишь один простой API-вызов¹⁷:

Процесс генерации памяти можно сравнить с работой заботливого садовника, ухаживающего за садом.
Извлечение (Extraction) — это как получение новых семян и саженцев (новая информация из диалога). Садовник не просто беспорядочно разбрасывает их по участку. Вместо этого он выполняет Объединение (Consolidation): вырывает сорняки (удаляет избыточные или конфликтующие данные), подрезает разросшиеся ветви, чтобы улучшить здоровье существующих растений (уточняет и обобщает существующие записи), а затем аккуратно высаживает новые саженцы в оптимальном месте.
Такой постоянный, вдумчивый уход гарантирует, что сад остаётся здоровым, организованным и продолжает процветать с течением времени, а не превращается в заросшие, непроходимые дебри. Этот асинхронный процесс происходит в фоновом режиме, обеспечивая, чтобы сад всегда был готов к следующему «визиту».
Теперь давайте подробнее рассмотрим два ключевых этапа генерации памяти: извлечение и объединение.
Глубокое погружение: извлечение памяти (Memory Extraction)
Цель извлечения памяти — ответить на фундаментальный вопрос: «Какая информация в этом диалоге достаточно значима, чтобы стать „воспоминанием“?» Это не простое суммирование; это целенаправленный, интеллектуальный процесс фильтрации, предназначенный для отделения сигнала (важные факты, предпочтения, цели) от шума (любезности, слова-«наполнители»).
«Значимость» — это не универсальное понятие; она полностью определяется целью и сценарием использования агента. То, что нужно помнить агенту поддержки (например, номера заказов, технические проблемы), кардинально отличается от того, что нужно помнить персональному велнес-коучу (например, долгосрочные цели, эмоциональное состояние). Поэтому настройка того, какая информация сохраняется, является ключом к созданию по-настоящему эффективного агента.
LLM менеджер памяти решает, что извлекать, следуя тщательно продуманному набору программных ограничений (guardrails) и инструкций, обычно встроенных в сложный системный промпт. Этот промпт определяет, что значит «значимый», предоставляя LLM набор определений тем (topic definitions).
Извлечение на основе схемы или шаблона: LLM предоставляется заранее определённая JSON-схема или шаблон, использующий такие функции LLM, как структурированный вывод¹⁸. LLM получает инструкцию сформировать JSON, используя соответствующую информацию из диалога.
Определение тем на естественном языке: LLM руководствуется простым описанием темы на естественном языке.
Промптинг с несколькими примерами (Few-shot prompting): LLM «показывают», какую информацию извлекать, на примерах. Промпт включает несколько образцов входного текста и идеальную, качественную запись, которую следует извлечь. LLM изучает желаемый паттерн извлечения по примерам, что делает этот метод высокоэффективным для нестандартных или тонких тем, которые трудно описать с помощью схемы или простого определения.
Большинство менеджеров памяти «из коробки» ищут распространённые темы, такие как предпочтения пользователя, ключевые факты или цели. Многие платформы также позволяют разработчикам определять свои собственные темы, адаптируя процесс извлечения к своей специфической области.
Например, вы можете настроить, какую информацию Agent Engine Memory Bank должен считать значимой для сохранения, предоставив свои собственные определения тем и примеры¹⁹:


Хотя само по себе извлечение памяти — это не «суммаризация», алгоритм может включать в себя суммаризацию для концентрации информации.
Для повышения эффективности многие менеджеры памяти встраивают «скользящую сводку» (rolling summary) диалога непосредственно в промпт для извлечения памяти²⁰. Эта сжатая история предоставляет необходимый контекст для извлечения ключевой информации из самых последних взаимодействий. Это устраняет необходимость на каждом шаге (turn) заново обрабатывать полный, подробный диалог для поддержания контекста.
После того как информация извлечена из источника данных, существующий корпус памяти должен быть обновлён, чтобы отразить эту новую информацию, — через процесс объединения (consolidation).
Глубокое погружение: объединение памяти (Memory Consolidation)
После того как «воспоминания» извлечены из подробного диалога, процесс объединения (consolidation) должен интегрировать эту новую информацию в целостную, точную и развивающуюся базу знаний. Это, пожалуй, самый сложный этап в жизненном цикле памяти, который превращает простую коллекцию фактов в тщательно курируемое понимание пользователя. Без объединения память агента быстро превратилась бы в «зашумлённый», противоречивый и ненадёжный лог каждой когда-либо зафиксированной крупицы информации.
Это «само-курирование», обычно управляемое LLM, и есть то, что возвышает менеджер памяти над простой базой данных.
Объединение решает фундаментальные проблемы, возникающие при работе с данными из диалогов, в том числе:
Дублирование информации: Пользователь может упомянуть один и тот же факт разными способами в разных диалогах (например, «Мне нужен рейс в НЙ» и позже «Я планирую поездку в Нью-Йорк»). Простой процесс извлечения создал бы две избыточные записи.
Противоречивая информация: Состояние пользователя меняется со временем. Без объединения память агента содержала бы противоречивые факты.
Эволюция информации: Простой факт может стать более детальным. Изначальная запись «пользователь интересуется маркетингом» может развиться в «пользователь возглавляет маркетинговый проект, сфокусированный на привлечении клиентов в 4 квартале».
Устаревание памяти (Memory Relevance Decay): Не все воспоминания остаются полезными вечно. Агент должен уметь «забывать» — проактивно удалять старые, неактуальные или маловероятные записи, чтобы поддерживать базу знаний релевантной и эффективной. «Забывание» может происходить путём инструктирования LLM отдавать предпочтение более новой информации во время объединения или через автоматическое удаление по истечении срока жизни (TTL).
Процесс объединения — это управляемый LLM рабочий процесс, который сравнивает вновь извлечённые данные с существующими записями пользователя.
Сначала он пытается найти существующие записи, похожие на новые. Эти записи становятся кандидатами на объединение. Если существующая запись противоречит новой информации, она может быть удалена. Если дополняется — обновлена.
-
Затем LLM предоставляются и существующие, и новые данные. Её основная задача — проанализировать их вместе и определить, какие операции следует выполнить. Основные операции включают:
UPDATE (Обновить): Изменить существующую запись, добавив новую или исправленную информацию.
CREATE (Создать): Если новая информация совершенно уникальна и не связана с существующими записями, создать новую.
DELETE / INVALIDATE (Удалить / Сделать неактуальной): Если новая информация делает старую запись полностью нерелевантной или неверной, удалить или пометить её как неактуальную.
Наконец, менеджер памяти преобразует решение LLM в транзакцию, которая обновляет хранилище памяти.
Происхождение данных в памяти (Memory Provenance)
Классическая аксиома машинного обучения «мусор на входе — мусор на выходе» (garbage in, garbage out) ещё более актуальна для LLM, где результат часто описывается как «мусор на входе — уверенный бред на выходе» (garbage in, confident garbage out).
Чтобы агент мог принимать надёжные решения, а менеджер памяти — эффективно объединять данные, они должны уметь критически оценивать качество своих собственных «воспоминаний». Эта надёжность напрямую зависит от происхождения (provenance) записи в памяти — детальной истории её источника и изменений.

Процесс объединения (consolidation) памяти — слияние информации из нескольких источников в единую, развивающуюся запись — создаёт необходимость отслеживать её «родословную» (lineage). Как показано на диаграмме выше, одна запись в памяти может быть результатом смешения нескольких источников данных, а один источник — разделён на несколько записей.
Чтобы оценить надёжность, агент должен отслеживать ключевые детали по каждому источнику, такие как его происхождение (тип источника) и возраст («свежесть»). Эти детали критически важны по двум причинам: они определяют вес, который имеет каждый источник во время объединения памяти, и они подсказывают агенту, насколько он должен полагаться на эту память во время логических выводов.
Тип источника — один из самых важных факторов в определении доверия. Источники данных делятся на три основные категории:
Начальные данные (Bootstrapped Data): Информация, предварительно загруженная из внутренних систем, таких как CRM. Эти данные с высоким уровнем доверия могут использоваться для инициализации памяти пользователя, чтобы решить проблему «холодного старта» — сложность предоставления персонализированного опыта пользователю, с которым агент никогда раньше не взаимодействовал.
Данные от пользователя (User Input): Сюда входят данные, предоставленные явно (например, через форму, что заслуживает высокого доверия), или информация, извлечённая неявно из диалога (которая, как правило, менее надёжна).
Результаты работы инструментов (Tool Output): Данные, возвращённые после вызова внешнего инструмента. Создание записей в памяти из результатов работы инструментов, как правило, не рекомендуется, потому что такие «воспоминания» имеют тенденцию быть хрупкими (brittle) и быстро устаревать (stale), что делает этот тип источника более подходящим для краткосрочного кэширования.
Учёт происхождения данных при управлении памятью
Такой динамический, многоисточниковый подход к памяти создаёт две основные операционные проблемы при её управлении: разрешение конфликтов и удаление производных данных.
Объединение памяти (consolidation) неизбежно приводит к ситуациям, когда один источник данных противоречит другому. Происхождение (provenance) записи позволяет менеджеру памяти установить иерархию доверия для своих источников информации. Когда записи из разных источников противоречат друг другу, агент должен использовать эту иерархию в стратегии разрешения конфликтов. Распространённые стратегии включают:
Приоритет наиболее надёжного источника.
Предпочтение самой свежей информации.
Поиск подтверждения из нескольких источников.
Ещё одна сложность возникает при удалении данных. Одна запись в памяти может быть производной от нескольких источников. Когда пользователь отзывает доступ к одному из них, данные, полученные из этого источника, также должны быть удалены. Удаление каждой записи, «затронутой» этим источником, может быть слишком агрессивным подходом. Более точный, хотя и вычислительно затратный, метод — пересоздать затронутые записи с нуля, используя только оставшиеся, валидные источники.
Помимо статических данных о происхождении, уверенность (confidence) в записи должна меняться со временем. Уверенность растёт через подтверждение (corroboration), например, когда несколько надёжных источников предоставляют согласующуюся информацию.
Однако эффективная система памяти должна также активно курировать свои существующие знания через «чистку» памяти (memory pruning) — процесс, который выявляет и «забывает» записи, которые больше не являются полезными. Эта «чистка» может быть вызвана несколькими факторами:
Устаревание со временем (Time-based Decay): Важность записи может со временем уменьшаться. Запись о встрече двухлетней давности, скорее всего, менее релевантна, чем о встрече на прошлой неделе.
Низкая уверенность (Low Confidence): Запись, созданная на основе слабого логического вывода и так и не подтверждённая другими источниками, может быть удалена.
Нерелевантность (Irrelevance): По мере того как агент глубже понимает пользователя, он может определить, что некоторые старые, тривиальные записи больше не соответствуют текущим целям пользователя.
Сочетая реактивный конвейер объединения с проактивной «чисткой», менеджер памяти гарантирует, что база знаний агента — это не просто растущий лог всего, что когда-либо было сказано. Вместо этого, это тщательно курируемое, точное и релевантное понимание пользователя.
Учёт происхождения данных во время логических выводов (inference)
Помимо учёта происхождения (lineage) при курировании содержимого корпуса, надёжность записи также следует учитывать во время логических выводов (inference time). Уверенность агента в записи не должна быть статичной; она должна меняться на основе новой информации и течения времени.
Уверенность растёт через подтверждение (corroboration), например, когда несколько надёжных источников предоставляют согласующуюся информацию. И наоборот, уверенность уменьшается (или затухает) со временем, когда старые записи устаревают, а также падает, когда появляется противоречивая информация. В конечном итоге система может «забыть» данные, архивируя или удаляя записи с низкой степенью уверенности.
Этот динамический показатель уверенности (confidence score) критически важен во время логических выводов. Записи из памяти и, если доступны, их показатели уверенности, внедряются в промпт, позволяя LLM оценивать надёжность информации и принимать более тонкие решения.
Вся эта система оценки доверия служит для внутреннего процесса рассуждений агента. Сами записи и их показатели уверенности обычно не показываются пользователю напрямую. Вместо этого они внедряются в системный промпт, позволяя LLM взвешивать доказательства, учитывать надёжность своей информации и, в конечном счёте, принимать более взвешенные и заслуживающие доверия решения.
Запуск генерации памяти
Хотя менеджеры памяти автоматизируют извлечение и объединение данных после запуска генерации, агент всё равно должен решать, когда следует пытаться сгенерировать запись. Это критически важный архитектурный выбор, балансирующий между свежестью данных, вычислительными затратами и задержками (latency).
Это решение обычно управляется логикой агента, которая может использовать несколько стратегий запуска. Генерация памяти может быть инициирована на основе различных событий:
Завершение сессии: Запуск генерации в конце многоходовой сессии.
Периодичность по шагам (Turn Cadence): Запуск процесса после определённого количества шагов (например, каждые 5 шагов).
В реальном времени (Real-Time): Генерация после каждого шага диалога.
Явная команда (Explicit Command): Активация процесса по прямой команде пользователя (например, «Запомни это»).
Выбор триггера — это прямой компромисс между стоимостью и точностью (fidelity). Частая генерация (например, в реальном времени) гарантирует, что записи будут очень подробными и свежими, фиксируя каждый нюанс. Однако это влечёт за собой самые высокие затраты на LLM и базу данных и может вызывать задержки, если не обрабатывается должным образом. Нечастая генерация (например, по завершении сессии) гораздо более экономична, но рискует создавать менее точные записи, поскольку LLM приходится суммировать гораздо больший блок диалога за один раз. Также следует убедиться, что менеджер памяти не обрабатывает одни и те же события несколько раз, так как это приводит к ненужным затратам.
Память как инструмент (Memory-as-a-Tool)
Более продвинутый подход — позволить агенту самому решать, когда создавать запись в памяти.
В этом паттерне генерация памяти представляется в виде инструмента (например, create_memory). В описании этого инструмента должно быть указано, какие типы информации следует считать значимыми. Агент затем может анализировать диалог и автономно принимать решение вызвать этот инструмент, когда он обнаружит информацию, которую стоит сохранить.
Это перекладывает ответственность за определение «значимой информации» с внешнего менеджера памяти на самого агента (и, следовательно, на вас как на разработчика).
Например, в ADK вы можете сделать это, упаковав ваш код для генерации памяти в Инструмент (Tool)²¹, который агент будет вызывать, когда сочтёт, что диалог содержит что-то важное для сохранения. Вы можете отправить Session в Memory Bank, и Memory Bank извлечёт и объединит данные из истории диалога:

Другой подход — использовать внутреннюю память, где агент активно решает, что запомнить из диалога. В этом рабочем процессе агент сам отвечает за извлечение ключевой информации.
Опционально, эти извлечённые «воспоминания» затем могут быть отправлены в Agent Engine Memory Bank для их объединения (consolidation) с существующими данными пользователя²²:

Фоновые и блокирующие операции
Генерация памяти — это ресурсоёмкая операция, требующая LLM-вызовов и записей в базу данных. Для агентов в продакшене генерация памяти почти всегда должна выполняться асинхронно, как фоновый процесс²³.
После того как агент отправил ответ пользователю, конвейер генерации памяти может работать параллельно, не блокируя пользовательский опыт. Такое разделение (decoupling) необходимо, чтобы агент оставался быстрым и отзывчивым. Блокирующий (синхронный) подход, при котором пользователю пришлось бы ждать, пока запись в память будет завершена, прежде чем получить ответ, создал бы недопустимо медленный и разочаровывающий пользовательский опыт. Это требует, чтобы генерация памяти происходила в сервисе, архитектурно отделённом от основной среды выполнения (runtime) агента.
Извлечение памяти (Memory Retrieval)
Когда механизм генерации памяти настроен, ваше внимание может переключиться на критически важную задачу — извлечение (retrieval). Интеллектуальная стратегия извлечения необходима для производительности агента и включает в себя решения о том, какие «воспоминания» следует извлекать и когда это делать.
Стратегия извлечения сильно зависит от того, как организована память.
Для структурированного профиля пользователя извлечение — это, как правило, простой поиск всего профиля или конкретного атрибута.
Для коллекции «воспоминаний», однако, извлечение — это гораздо более сложная задача поиска. Цель состоит в том, чтобы найти наиболее релевантную, концептуально связанную информацию в большом пуле неструктурированных или полуструктурированных данных.
Стратегии, обсуждаемые в этом разделе, предназначены для решения этой сложной задачи извлечения из коллекций памяти.
Извлечение памяти (memory retrieval) — это поиск наиболее релевантных «воспоминаний» для текущего диалога. Эффективная стратегия извлечения критически важна: предоставление нерелевантной информации может запутать модель и ухудшить её ответ, в то время как идеально подобранный фрагмент контекста может привести к поразительно интеллектуальному взаимодействию. Основная задача — сбалансировать «полезность» памяти в рамках строгого бюджета по задержкам (latency).
Продвинутые системы памяти выходят за рамки простого поиска и оценивают потенциальные «воспоминания» по нескольким параметрам, чтобы найти наилучшее совпадение.
Релевантность (семантическое сходство): Насколько концептуально эта запись связана с текущим диалогом?
Свежесть (временной фактор): Как давно была создана эта запись?
Важность (значимость): Насколько критична эта запись в целом? В отличие от релевантности, «важность» может быть определена ещё на этапе генерации.
Распространённая ошибка — полагаться исключительно на релевантность, определённую на основе векторов. Оценки сходства могут «поднять наверх» записи, которые концептуально похожи, но стары или тривиальны. Наиболее эффективная стратегия — это смешанный подход, который комбинирует оценки по всем трём параметрам.
Для приложений, где точность имеет первостепенное значение, извлечение можно улучшить с помощью таких подходов, как переформулирование запроса (query rewriting), переранжирование (reranking) или специализированные ретриверы. Однако эти техники вычислительно затратны и добавляют значительные задержки, что делает их неподходящими для большинства приложений, работающих в реальном времени. В сценариях, где эти сложные алгоритмы необходимы, а данные устаревают не слишком быстро, эффективным решением может стать слой кэширования. Кэширование позволяет временно сохранять дорогостоящие результаты запроса, избегая высоких задержек при последующих идентичных запросах.
При переформулировании запроса LLM может использоваться для улучшения самого поискового запроса. Это может включать преобразование неоднозначного ввода пользователя в более точный запрос или расширение одного запроса до нескольких связанных, чтобы охватить разные аспекты темы. Хотя это значительно улучшает качество первоначальных результатов поиска, это добавляет задержку ещё одного LLM-вызова в начале процесса.
При переранжировании первоначальный поиск извлекает широкий набор кандидатов (например, топ-50 результатов) с помощью поиска по сходству. Затем LLM может повторно оценить и переранжировать этот меньший набор, чтобы составить более точный итоговый список²⁴.
Наконец, можно обучить специализированный ретривер с помощью дообучения (fine-tuning). Однако это требует доступа к размеченным данным и может значительно увеличить затраты.
В конечном счёте, лучший подход к извлечению начинается с качественного формирования самой памяти. Обеспечение того, чтобы корпус памяти был высококачественным и свободным от нерелевантной информации, — это самый эффективный способ гарантировать, что любой набор извлечённых «воспоминаний» будет полезен.
Выбор времени для извлечения (Timing for retrieval)
Заключительный архитектурный вопрос при работе с извлечением — это когда именно извлекать данные из памяти.
Один из подходов — проактивное извлечение (proactive retrieval), при котором данные из памяти автоматически загружаются в начале каждого шага (turn) диалога. Это гарантирует, что контекст всегда доступен, но приводит к ненужным задержкам (latency) на тех шагах, которые не требуют доступа к памяти. Поскольку данные в памяти остаются статичными в течение одного шага, их можно эффективно кэшировать, чтобы компенсировать эти потери в производительности.
Например, в ADK вы можете реализовать проактивное извлечение, используя встроенный PreloadMemoryTool или кастомный коллбэк (custom callback)²⁵:

Альтернативный подход — реактивное извлечение (reactive retrieval), или «Память как инструмент». В этом случае агенту предоставляется инструмент для запроса к своей памяти, и он сам решает, когда ему нужно извлечь контекст.
Этот метод более эффективен и надёжен, но требует дополнительного LLM-вызова, что увеличивает задержки (latency) и стоимость. Однако память извлекается только тогда, когда это действительно необходимо, поэтому дополнительные затраты на задержку возникают реже.
Кроме того, агент может не знать, существует ли релевантная информация, которую можно было бы извлечь. Эту проблему можно смягчить, проинформировав агента о типах доступных «воспоминаний» (например, в описании инструмента, если вы используете кастомный инструмент), что позволит ему принимать более обоснованное решение о том, когда делать запрос.

Использование памяти при формировании ответа (Inference with Memories)
После того как релевантные данные извлечены из памяти, заключительный этап — их грамотное размещение в контекстном окне модели. Это критически важный процесс, поскольку то, где именно находятся эти данные, может значительно повлиять на логику рассуждений LLM, операционные затраты и, в конечном итоге, на качество финального ответа.
Данные из памяти в основном представляются двумя способами: добавлением в системные инструкции или внедрением в историю диалога.
На практике гибридная стратегия часто оказывается наиболее эффективной.
Используйте системный промпт для стабильных, глобальных «воспоминаний» (таких как профиль пользователя), которые должны присутствовать всегда.
В остальных случаях используйте внедрение в диалог или подход «Память как инструмент» для временных, эпизодических данных, которые релевантны только для текущего контекста диалога.
Это позволяет сбалансировать потребность в постоянном (persistent) контексте с гибкостью извлечения информации по мере необходимости.
Данные из памяти в системных инструкциях
Простой способ использовать память при формировании ответа — добавить (append) извлечённые данные в системные инструкции.
Этот метод сохраняет историю диалога чистой, поскольку извлечённые «воспоминания» добавляются напрямую в системный промпт вместе с преамбулой, представляя их как фундаментальный контекст для всего взаимодействия.
Например, вы можете использовать Jinja для динамического добавления данных из памяти в ваши системные инструкции:

Включение данных в системные инструкции наделяет их высоким приоритетом, чётко отделяет контекст от диалога и идеально подходит для стабильной, «глобальной» информации, такой как профиль пользователя. Однако существует риск чрезмерного влияния, когда агент может пытаться привязать любую тему к информации из своих базовых инструкций, даже если это неуместно.
Этот архитектурный паттерн накладывает несколько ограничений.
Во-первых, он требует, чтобы фреймворк агента поддерживал динамическое формирование системного промпта перед каждым вызовом LLM, а такая функциональность доступна не всегда.
Во-вторых, паттерн несовместим с подходом «Память как инструмент», поскольку системный промпт должен быть сформирован до того, как LLM сможет решить вызвать инструмент для извлечения данных.
Наконец, он плохо справляется с нетекстовыми данными: большинство LLM принимают в качестве системных инструкций только текст, что усложняет прямое встраивание мультимодального контента, такого как изображения или аудио.
Данные из памяти в истории диалога
При этом подходе извлечённые данные внедряются (inject) непосредственно в пошаговый диалог. Их можно поместить либо перед всей историей диалога, либо непосредственно перед последним запросом пользователя.
Однако этот метод может создавать информационный шум, увеличивая затраты на токены и потенциально путая модель, если извлечённые данные нерелевантны. Основной риск — это «внедрение в диалог» (dialogue injection), когда модель может ошибочно принять данные из памяти за реплику, которая действительно была произнесена в диалоге. Также нужно быть осторожнее с тем, от чьего лица сформулированы внедряемые данные. Например, если вы используете роль «user» и данные уровня пользователя, они должны быть написаны от первого лица.
Частным случаем внедрения в историю диалога является извлечение данных через вызовы инструментов. В этом случае «воспоминания» будут включены непосредственно в диалог как часть ответа от инструмента.

Процедурная память
Этот материал был в основном сосредоточен на декларативной памяти, что отражает текущее состояние рынка решений для управления памятью. Большинство платформ также спроектированы для этого декларативного подхода, преуспевая в извлечении, хранении и получении ответа на вопрос «что?» — фактов, истории и данных о пользователе.
Однако эти системы не предназначены для управления процедурной памятью — механизмом для улучшения рабочих процессов и логики рассуждений агента. Хранение ответа на вопрос «как?» — это не задача по извлечению информации, а задача по расширению возможностей рассуждения (reasoning augmentation).
Управление этим «знанием как» требует совершенно отдельного и специализированного алгоритмического жизненного цикла, хотя и с похожей высокоуровневой структурой²⁶:
Извлечение: Извлечение процедурных данных требует специализированных промптов, предназначенных для того, чтобы «выкристаллизовать» переиспользуемую стратегию или «план действий» из успешного взаимодействия, а не просто зафиксировать факт или значимую информацию.
Объединение (Consolidation): В то время как декларативное объединение сливает связанные факты («что»), процедурное объединение курирует сам рабочий процесс («как»). Это активный процесс управления логикой, сфокусированный на интеграции новых успешных методов с существующими «лучшими практиками», исправлении ошибочных шагов в известном плане и удалении устаревших или неэффективных процедур.
Извлечение (Retrieval): Цель состоит не в том, чтобы получить данные для ответа на вопрос, а в том, чтобы получить план, который будет направлять агента при выполнении сложной задачи. Поэтому процедурные данные могут иметь иную схему, нежели декларативные.
Эта способность агента к «самоэволюции» своей логики, естественно, напрашивается на сравнение с распространённым методом адаптации: дообучением (fine-tuning) — часто с помощью Reinforcement Learning from Human Feedback (RLHF)²⁷.
Хотя оба процесса направлены на улучшение поведения агента, их механизмы и применение коренным образом различаются.
Дообучение — это относительно медленный, оффлайн-процесс тренировки, который изменяет веса модели.
Процедурная память обеспечивает быструю, онлайн-адаптацию, динамически внедряя правильный «план действий» в промпт и направляя агента через обучение в контексте (in-context learning) без необходимости какого-либо дообучения.
Тестирование и оценка
Теперь, когда у вас есть агент, оснащённый памятью, вам следует проверить его поведение с помощью всестороннего тестирования и оценки качества.
Оценка памяти агента — это многоуровневый процесс. Необходимо убедиться, что агент запоминает правильные вещи (качество), что он может найти эти «воспоминания», когда они нужны (извлечение), и что их использование действительно помогает ему достигать своих целей (успех задачи). В то время как академическая среда фокусируется на воспроизводимых бенчмарках, на практике оценка сосредоточена на том, как память напрямую влияет на производительность и удобство использования агента в рабочей среде.
Метрики качества генерации памяти
Эти метрики оценивают содержимое самих «воспоминаний», отвечая на вопрос: «Запоминает ли агент то, что нужно?». Обычно это измеряется путём сравнения сгенерированных агентом данных с вручную созданным «эталонным набором» (golden set) идеальных «воспоминаний».
Точность (Precision): Какой процент созданных агентом записей является точным и релевантным? Высокая точность защищает от «слишком усердной» системы, которая засоряет базу знаний нерелевантным шумом.
Полнота (Recall): Какой процент всех релевантных фактов, которые агент должен был запомнить, он действительно зафиксировал? Высокая полнота гарантирует, что агент не упускает критически важную информацию.
F1-Score: Гармоническое среднее между точностью и полнотой, предоставляющее единую, сбалансированную метрику качества.
Метрики производительности извлечения памяти
Эти метрики оценивают способность агента находить нужную запись в нужное время.
Recall@K: Когда требуется «воспоминание», находится ли правильное среди K верхних результатов поиска? Это основная метрика точности системы извлечения.
Задержка (Latency): Извлечение находится на «критическом пути» (hot path) ответа агента. Весь процесс должен выполняться в рамках строгих временных рамок (например, менее 200 мс), чтобы не ухудшать пользовательский опыт.
Итоговые метрики успеха задачи (End-to-End)
Это главная проверка, отвечающая на вопрос: «Действительно ли память помогает агенту лучше выполнять свою работу?». Это измеряется путём оценки производительности агента на последующих задачах (downstream tasks) с использованием его памяти. Часто для этого используется LLM в роли «судьи», который сравнивает итоговый результат агента с эталонным ответом.
Оценка — это не разовое событие, а механизм для постоянного совершенствования. Приведённые выше метрики предоставляют данные, необходимые для выявления слабых мест и систематического улучшения системы памяти с течением времени.
Хотя метрики выше сосредоточены на качестве, готовность к продакшену (production-readiness) также зависит от производительности. Для каждой области оценки критически важно измерять задержку базовых алгоритмов и их способность масштабироваться под нагрузкой. Извлечение на «критическом пути» может иметь строгие рамки по времени отклика, не превышающие долей секунды. Генерация и объединение, хотя часто и асинхронны, должны иметь достаточную пропускную способность, чтобы справляться с пользовательской нагрузкой. В конечном итоге, успешная система памяти должна быть интеллектуальной, эффективной и надёжной для использования в реальных условиях.
Требования к Памяти в рабочей среде (Production)
Помимо производительности, перевод агента с памятью от прототипа к продакшену требует особого внимания к архитектурным аспектам корпоративного уровня. Этот переход выдвигает критические требования к масштабируемости, отказоустойчивости и безопасности. Система промышленного уровня должна быть спроектирована не только для интеллектуальной работы, но и для обеспечения надёжности корпоративного класса.
Чтобы пользовательский опыт никогда не блокировался из-за вычислительно затратного процесса генерации памяти, надёжная архитектура должна отделять (decouple) обработку памяти от основной логики приложения. Хотя это событийно-ориентированный an event-driven паттерн, он обычно реализуется через прямые, неблокирующие API-вызовы к выделенному сервису памяти, а не через самостоятельно управляемую очередь сообщений. Процесс выглядит так:
Агент отправляет данные: После релевантного события (например, завершения сессии) приложение агента делает неблокирующий API-вызов к менеджеру памяти, «отправляя» ему для обработки «сырые» исходные данные (например, стенограмму диалога).
Менеджер памяти обрабатывает данные в фоновом режиме: Сервис менеджера памяти немедленно подтверждает получение запроса и помещает задачу на генерацию в свою собственную, внутреннюю управляемую очередь. После этого он берёт на себя всю ресурсоёмкую асинхронную работу: делает необходимые LLM-вызовы для извлечения, объединения и форматирования данных. Менеджер может отложить обработку до тех пор, пока не пройдёт определённый период неактивности.
Данные сохраняются: Сервис записывает итоговые «воспоминания» — будь то новые записи или обновления существующих — в выделенную, надёжную базу данных. В управляемых менеджерах памяти хранилище является встроенным.
Агент извлекает данные: Основное приложение агента может затем напрямую запрашивать это хранилище, когда ему нужен контекст для нового взаимодействия с пользователем.
Такой сервисный, неблокирующий подход гарантирует, что сбои или задержки в конвейере обработки памяти не влияют напрямую на приложение, с которым работает пользователь, делая систему гораздо более отказоустойчивой (resilient). Это также определяет выбор между онлайн-генерацией (в реальном времени), идеальной для поддержания актуальности диалога, и оффлайн-обработкой (пакетной), которая полезна для наполнения системы историческими данными.
По мере роста приложения система памяти должна справляться с высокочастотными событиями без сбоев. При одновременных запросах система должна предотвращать взаимоблокировки (deadlocks) или состояния гонки (race conditions), когда несколько событий пытаются изменить одну и ту же запись. Снизить риск состояний гонки можно, используя транзакционные операции с базой данных или оптимистичные блокировки (optimistic locking).
Сервис памяти также должен быть устойчив к временным ошибкам. Если LLM-вызов завершается неудачно, система должна использовать механизм повторных попыток с экспоненциальной задержкой (exponential backoff) и направлять постоянные ошибки в очередь «мёртвых» сообщений (dead-letter queue) для анализа.
Для глобальных приложений менеджер памяти должен использовать базу данных со встроенной межрегиональной репликацией для обеспечения низких задержек и высокой доступности. Репликация на стороне клиента нецелесообразна, поскольку для объединения данных требуется единое, транзакционно-целостное представление данных, чтобы предотвратить конфликты.
Управляемые системы памяти, такие как Agent Engine Memory Bank, должны помочь вам решить эти задачи, чтобы вы могли сосредоточиться на основной логике агента.
Риски для конфиденциальности и безопасности
Данные в памяти создаются на основе пользовательских данных и включают их, поэтому они требуют строжайших мер контроля конфиденциальности и безопасности. Полезная аналогия — представить память системы как защищённый корпоративный архив, которым управляет профессиональный архивариус, чья работа — сохранять ценные знания, защищая при этом компанию.
Кардинальное правило для этого архива — изоляция данных. Точно так же, как архивариус никогда не смешает конфиденциальные файлы из разных отделов, память должна быть строго изолирована на уровне пользователя или клиента (tenant). Агент, обслуживающий одного пользователя, никогда не должен иметь доступа к «воспоминаниям» другого. Это обеспечивается с помощью ограничительных списков контроля доступа (ACL). Кроме того, пользователи должны иметь программный контроль над своими данными, с чёткими опциями для отказа от генерации памяти или запроса на удаление всех их «файлов» из архива.
Перед тем как подшить любой документ, архивариус выполняет критически важные шаги.
Во-первых, он тщательно просматривает каждую страницу, чтобы удалить (redact) конфиденциальную личную информацию (PII), гарантируя, что знания сохраняются, не создавая при этом юридических рисков (liability).
Во-вторых, архивариус обучен распознавать и отбрасывать подделки или намеренно вводящие в заблуждение документы — это защита от отравления памяти (memory poisoning)²⁸.
Точно так же система должна проверять и очищать (sanitize) информацию, прежде чем сохранять её в долговременную память, чтобы не позволить злоумышленнику повредить постоянные знания агента через prompt injection. Система должна включать такие защитные механизмы, как Model Armor, для валидации и очистки информации²⁹.
Кроме того, существует риск утечки (exfiltration), если несколько пользователей совместно используют один и тот же набор «воспоминаний», как в случае с процедурной памятью (которая учит агента, как что-то делать). Например, если процедурная память от одного пользователя используется в качестве примера для другого — подобно распространению служебной записки по всей компании — архивариус должен сначала выполнить строгую анонимизацию, чтобы предотвратить утечку конфиденциальной информации между пользователями.
Заключение
В этом материале мы рассмотрели дисциплину Context Engineering (инженерии контекста), сосредоточившись на двух её центральных компонентах: Сессиях и Памяти. Путь от простого шага в диалоге до фрагмента постоянного, действенного знания (actionable intelligence) управляется именно этой практикой, которая заключается в динамической сборке всей необходимой информации — включая историю диалога, «воспоминания» и внешние знания — в контекстном окне LLM. Весь этот процесс опирается на взаимодействие двух разных, но взаимосвязанных систем: краткосрочной Сессии и долговременной Памяти.
Сессия управляет «настоящим моментом», выступая в роли хронологического контейнера с низкой задержкой (low-latency) для одного диалога. Её основные вызовы — это производительность и безопасность, требующие быстрого доступа и строгой изоляции. Чтобы предотвратить переполнение контекстного окна и задержки, необходимо использовать такие методы извлечения, как усечение по токенам или рекурсивная суммаризация, для сжатия содержимого.
Память — это двигатель долгосрочной персонализации и основной механизм для сохранения данных между несколькими сессиями. Она идёт дальше, чем RAG (который делает агента экспертом по фактам), и делает агента экспертом по пользователю. Память — это активный, управляемый LLM ETL-конвейер, отвечающий за извлечение, объединение и получение данных, который «дистиллирует» самую важную информацию из истории диалога. Чтобы поддерживать отзывчивость пользовательского интерфейса, генерация памяти должна работать как асинхронный фоновый процесс, запускаемый после того, как агент ответил.
Отслеживая происхождение (provenance) данных и применяя защитные меры от таких рисков, как отравление памяти, разработчики могут создавать надёжных, адаптивных помощников, которые действительно учатся и развиваются вместе с пользователем.