Skip to main content
Glama
thomaskawas

agent-context-substrate

by thomaskawas

agent-context-substrate

Субстрат — это актив; модель — взаимозаменяемый клиент.

git clone https://github.com/thomaskawas/agent-context-substrate.git
cd agent-context-substrate
make setup && make demo

Требования: Python 3.12+, Docker, make. make setup создаёт виртуальное окружение и устанавливает зависимости, около 1,4 ГБ, поскольку демо работает на CPU и пропускает CUDA-колёса; на медленном соединении дайте несколько минут. База данных привязывается к 127.0.0.1:5432, поэтому остановите всё, что уже занимает этот порт.

Один запрос, прослеженный через четыре этапа поиска, затем таблица абляции и базовый шлюз

Зачем это существует

Я создаю долгосрочные проекты с ИИ-агентами, и восстановление контекста в начале каждой сессии было налогом, который я платил чаще всего. Загрузка одних и тех же файлов, повторное объяснение одних и тех же решений, наблюдение за тем, как полезная часть окна заполняется материалом, который модель уже видела дважды. Выходила новая модель — и ничего из этого не переносилось. Проблема никогда не была в том, что контекст отсутствовал. Проблема была в том, что контекст не был адресуемым: не было способа задать вопрос и получить только то, что на него отвечает, поэтому вы отправляете всё и надеетесь. Решение состояло в том, чтобы перестать относиться к контексту как к чему-то, что вы приносите в сессию, и начать относиться к нему как к чему-то, что вы запрашиваете.

Эталонная реализация независимого от модели субстрата памяти для ИИ-агентов: память проекта живёт вне модели в запрашиваемом, версионируемом хранилище, доступном через единый MCP-шлюз. Меняйте модель — сохраняйте всё. Сегодня Claude, завтра Gemini или GPT, под ними та же память проекта. Вместо вставки истории в каждую сессию поиск выбирает небольшой набор записей, которые действительно нужны текущей задаче.

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

Ключи API не требуются: make demo работает полностью на локальных компонентах. Зафиксированные локальные модели (имя и ревизия) — это профиль адаптера по умолчанию, local (make warmup, запускается автоматически через make demo, предварительно загружает ~180 МБ один раз); герметичный профиль deterministic без загрузок поддерживает тесты и постоянно включённый CI-шлюз.

Related MCP server: AI Memory MCP Server

Структура

src/acs/adapters/base.py — это тезис в коде: четыре небольших интерфейса, за которыми стоит каждая внешняя возможность. src/acs/store/ рассматривает память как систему записи (версионируемую, аудируемую, по-настоящему удаляемую). src/acs/retrieval/ — это конвейер из небольших, отдельно тестируемых этапов. eval/ — это шлюз: изменения попадают в релиз, если соответствуют или превосходят baseline.lock.json, иначе не попадают.

Обоснование решений находится в docs/adr/: девять записей о решениях. Большинство — полстраницы; три длиннее, где аргументу нужно было место.

Также в docs/: architecture.md — зачем существует каждый слой, threat-model.md — о границах угроз и где находится каждая защита, principles.md — правила, из которых следует остальное, и build-your-own.md — последовательность сборки, которой следовал этот репозиторий.

Что это демонстрирует

  • Приём записывает оба представления за один проход: эмбеддинги для сходства, граф сущностей/связей для структуры. Каждый документ встраивается; документ, не содержащий связей, не добавляет рёбер.

  • Поиск — это конвейер из четырёх этапов: гибридный векторный + полнотекстовый поиск с настраиваемым смешиванием, мультизапросное слияние (RRF), переранжирование кросс-энкодером и раздел, привязанный к сущностям, где граф переупорядочивает переранжированный список, чтобы тематический ранжировщик перестал путать один компонент с его одноимённым собратом. Профили поиска для каждого потребителя — это данные, а не код.

  • Управление: изменения поиска попадают в релиз, если соответствуют или превосходят заблокированный базовый уровень оценки. Память версионируется по SCD2 с чтением на момент времени, очистка действительно удаляет (включая векторы), а журнал аудита отказывает в изменении на уровне базы данных.

  • Доступ: один MCP-шлюз предоставляет субстрат любому MCP-клиенту, с ограничением для каждого вызывающего. Карантинный исследовательский цикл заполняет пробелы с обязательным цитированием при обратной записи.

  • Переносимость: каждый провайдер стоит за адаптером; эмбеддер зафиксирован намеренно.

что вы хотите увидеть

команда

запрос, прослеженный через каждый этап поиска

make query Q="..."

бенчмарк абляции (recall@5, MRR на каждом этапе)

make bench

изменение поиска, проваливающее CI против заблокированного базового уровня

make check

идентичности памяти и полная цепочка версий одной памяти

make history

память, заменённая, но старая версия всё ещё читается

make supersede LINEAGE=<id> CONTENT="..."

чтение памяти на момент в прошлом

make asof LINEAGE=<id> TS=<timestamp>

субъект очищен, включая эмбеддинги

make purge SUBJECT=contributor-03

цепочки замены + соседи сущностей из графа

make graph ENTITY=CHG-4568

два ограниченных вызывающих на одном субстрате, один вызов отклонён

make gateway-client

исследовательский цикл заполняет пробел, с цитированием и в карантине

make research затем make vet

Идентификатор происхождения и временные метки берутся из make history: без аргументов он выводит текущие памяти с их идентификаторами; с LINEAGE=<id> он проходит по цепочке версий одной памяти и выводит окно действия каждой версии. Эти окна — ISO-временные метки, так что TS=, который вы вставляете, разрешается в версию, которую вы действительно читали, а не на секунду раньше или позже. Идентификаторы генерируются для каждого клона, поэтому ваши не совпадут с показанными здесь.

make purge действительно удаляет (включая цели золотого набора, когда они принадлежат очищенному субъекту), поэтому бенчмарк против очищенного корпуса отказывается запускаться как неполный, а не тихо сообщает о более низком recall. make demo сбрасывает к чистому корпусу.

Каждое число бенчмарка на этой странице получено из абляции на посеянном синтетическом корпусе (corpus/generate.py), воспроизводимо из чистого клона и контролируется в CI (профиль deterministic на каждом пуше, профиль local на метке bench-local) против заблокированного базового уровня, который также фиксирует дайджест корпуса. Читайте дельты, а не абсолюты: recall@5 / mrr@5 на синтетическом корпусе показывают, что даёт каждый этап, а не реальное качество. Чтобы увидеть, где этап зарабатывает свою дельту, запустите .venv/bin/python eval/run_benchmark.py --by-family.

Абляция, локальный профиль

этап

recall@5

mrr@5

что даёт этап

vector-only

0.6333

0.4340

пол: только сходство

+hybrid

0.9667

0.5742

recall. Лексический канал восстанавливает то, что пропускают эмбеддинги

+fusion

0.9750

0.6026

ранжирование, и почти без recall (recall +0.0083)

+rerank

0.9917

0.9072

ранжирование. mrr +0.3046 при recall, который почти не двигается

+graph

0.9917

0.9315

идентичность. Раздел сущностей, а не дополнительный поиск

Каждый этап даёт разное, что является аргументом в пользу конвейера, а не одного лучшего поисковика. tests/test_readme_table.py падает, если эта таблица и eval/baseline.lock.json когда-либо расходятся, поэтому таблица не может отклониться от чисел, которые обеспечивает шлюз. Шлюз — это нижняя граница, поэтому изменение, улучшающее метрику, проходит его, и числа здесь остаются до тех пор, пока базовый уровень не будет намеренно перезафиксирован с помощью make lock-baseline, что затем приводит к падению этой таблицы, пока она не будет приведена в соответствие. Локальный профиль, 120 золотых запросов, k=5, слияние этапа 1 rank, дайджест корпуса ad7bf7ca. Воспроизведите с помощью make demo.

Что эти числа поддерживают, а что нет, включая то, почему сравнение модельных дорожек является границей, а не кривой, изложено в docs/limitations.md.

A
license - permissive license
Not graded
quality - not tested
C
maintenance

Maintenance

Maintainers
Response time
Release cycle
Releases (12mo)
Commit activity

Resources

Unclaimed servers have limited discoverability.

Looking for Admin?

If you are the server author, to access and configure the admin panel.

Related MCP Servers

  • A
    license
    Not graded
    quality
    A
    maintenance
    Provides persistent, searchable memory for MCP-compatible agents, enabling recall by meaning, automatic decay, trust scoring, and cross-agent handoffs.
    4
    MIT
  • A
    license
    Not graded
    quality
    C
    maintenance
    Durable, inspectable memory for MCP agents. Preserves decisions, preferences, and project knowledge across sessions with full provenance and version history.
    2
    Apache 2.0
  • A
    license
    Not graded
    quality
    C
    maintenance
    Provides persistent, scoped shared memory for collaborating AI agents, with tools for storing observations, semantic recall, and handoff workflows. Backed by PostgreSQL and exposed through MCP.
    1
    Apache 2.0

View all related MCP servers

Related MCP Connectors

  • Shared, governed long-term memory for AI agents across tools and sessions via MCP and REST.

  • Your memory, everywhere AI goes. Build knowledge once, access it via MCP anywhere.

  • An MCP memory server. One memory your agents share — across models, devices and apps.

View all MCP Connectors

Latest Blog Posts

MCP directory API

We provide all the information about MCP servers via our MCP API.

curl -X GET 'https://glama.ai/api/mcp/v1/servers/thomaskawas/agent-context-substrate'

If you have feedback or need assistance with the MCP directory API, please join our Discord server