Memory

Keep durable, searchable context attached to the right member and organization across agent clients.

Memory preserves the part of an agent setup that should outlive a client or conversation. A user can move from Claude Code to Codex—or replace the agent entirely—without rebuilding stable preferences, facts, and project decisions.

The organization owns its memory. Each write is scoped as shared or private inside that organization, and CoreSpeed derives the caller identity from auth; the agent cannot supply a different user ID to cross the boundary. The boundary is enforced in Postgres by row-level security, not only in application code.

Tools

Names below are the operations exposed on the unified MCP surface:

ToolUse it for
memory__rememberSave one concise fact, preference, or decision.
memory__search_memoryFind memories relevant to the current task.
memory__get_memoryRead one memory in full by ID.
memory__ingestSave recent messages as memories, one memory per message.
memory__update_memoryCorrect an existing memory by ID — or, for a teammate's, propose the correction.
memory__delete_memoryRemove one of your own memories.
memory__list_memoryList memories newest first, a page at a time.
memory__clear_all_memoryDelete all memory after explicit confirmation.
memory__link_memoriesLink one of your memories to another one you can see.
memory__unlink_memoriesRemove one of those links.
memory__list_memory_linksList a memory's links, outbound or inbound.
memory__archive_memoryRetire a stale memory, naming the one that supersedes it.
memory__restore_memoryBring an archived memory back.
memory__list_memory_proposalsList proposed changes to memories you can see.
memory__withdraw_memory_proposalTake back a proposal you made.

These fifteen are the whole public surface — eleven for an organization without memory maintenance, which is served neither the last four nor the proposal path of memory__update_memory (see Keeping shared memory accurate). Retrieval underneath them is hybrid — exact and relaxed lexical matching, entity aliases, and vector similarity, fused into one ranking — but it is reached through memory__search_memory rather than exposed as separate knobs.

Long memories come back as excerpts

memory__search_memory and memory__list_memory return many memories at once, so they bound how much text each one contributes. A memory of 1,200 characters or fewer — the overwhelming majority — is returned whole. A longer one is returned as an excerpt, marked in the result:

{
  "id": "0b5f…",
  "memory": "Escalation runbook: page the on-call rotation first…",
  "truncated": true,
  "full_length": 5310
}

For a search hit the excerpt is the passage that actually matched the query, not the head of the memory — the same chunk the ranking scored. list_memory has no query to be relevant to, so it excerpts from the start.

Pass the id to memory__get_memory to read the whole thing. That read follows normal visibility: your own private memories plus the organization's shared ones, whoever wrote them.

A whole result is bounded too, not just each row in it. If the memories that matched would together exceed what a client can receive, the lowest-ranked ones are dropped and the result says how many:

{ "memories": [ /* … */ ], "omitted": 29 }

The top hit is always returned, however large. In practice the default limit of 10 never reaches the budget — only an explicitly high limit does. Narrow the query or lower limit to see what was dropped.

Shared and private context

memory__remember accepts scope: "shared" | "private":

  • private is the default and can be read only by the member who created it.
  • shared must be asked for explicitly, and can then be read by agents operating inside the same organization boundary.

Member state is always organization-scoped. Turning memory off in one organization cannot affect the same user in another organization.

A link is a durable, directed edge from a memory you own to any memory you can see, named by its two ids and a kind — "related" unless you choose another, such as "depends-on". "supersedes" is reserved: archiving writes it. The related_ids argument of memory__remember, memory__ingest, and memory__update_memory writes related links; memory__link_memories writes any kind, with an optional weight from 0 to 1.

Linking is safe to repeat: the same call again changes nothing, and a call with a new weight replaces the old one. memory__unlink_memories removes exactly the link its key names. memory__list_memory_links reads a memory's links back, newest first, and lists only links whose two memories you can see — a link to a teammate's private memory stays invisible to you, as that memory does.

The graph in Dashboard → Memory draws every link. A memory can hold up to 1,000 outgoing links and 16 kinds toward any one other memory; past a bound the call answers link_capacity_exceeded.

Keeping shared memory accurate

Memory maintenance — archive and restore, proposals, and version history — is rolling out organization by organization. Until yours has it, the archive, restore, and proposal tools are not in tools/list, a teammate's memory is changed only by its author, and the dashboard shows none of it.

A shared memory is read by every agent in the organization, so a stale one misleads all of them — and a correction saved next to it does not stop the old one being retrieved. Retire it instead:

  • Archive. memory__archive_memory takes the memory out of search, lists, and the memory index every session starts with. superseded_by names the memory that replaces it; reading the archived one by id says so. Nothing is deleted, and memory__restore_memory brings it back.
  • Your own memories are archived, restored, or corrected at once. So are an agent's memories for the member accountable for that agent.
  • A teammate's memory changes through a proposal. memory__update_memory, memory__archive_memory, and memory__restore_memory on it take a reason and answer status: "proposed". The memory's author — or an org admin — merges or rejects it in Dashboard → Memory → Proposals, like a pull request. An agent can propose but never merge.
  • A proposal is written against the memory's current version. If the memory changes before review, merging records the proposal as outdated and applies nothing; nothing is ever rebased.

Every change keeps the memory's three most recent prior versions, with who replaced each; the memory's page lists them and can restore one. Pending proposals expire after 30 days, and resolved ones leave after another 30.

Pricing and holds

Memory operations cost $0 per call. The provider remains inside the metered operating boundary, so an organization billing hold or suspension can still block execution. Storage quotas and rate limits protect the shared service.

Inspect and remove memory

Use Dashboard → Memory to browse memories, search, inspect the graph, open a detail view, and delete content — and, with memory maintenance, archive memories and review proposals. Disabling the memory capability hides its MCP tools but preserves existing data; deletion is a separate explicit action.

What belongs in memory

Save context that will improve a later action: a preference, a product decision, a named relationship, or an operating constraint. Do not use memory as a transcript archive, a secret store, or a substitute for application data.