ctx.memory
Scoped key-value and vector storage. Four scopes with different lifetimes and sharing rules — from ephemeral execution state to persistent user memory and shared suite context.
Why it exists
Correct lifecycle and portability. Execution = scratch; session = this conversation; persistent = forever (user-scoped); suite = shared across agents. Never replace with local variables or module state—you lose scope and audit.
How it makes life better
Use the four scopes and you get a clear contract: "scratch" vs "this session" vs "forever." Bypass with globals or ad-hoc storage and you get leaks, wrong lifetime, and no way to reason about what survives restarts.
The Four Scopes
// Four memory scopes, each with different lifetime and sharing rulesctx.memory.execution // Ephemeral — auto-cleaned after execution endsctx.memory.session // User session — hours to daysctx.memory.persistent // Long-term — user-scoped, survives restartsctx.memory.suite // Shared — all agents in the same suite can read/write| Scope | Lifetime | Shared with | Has Vector Store | Use for |
|---|---|---|---|---|
ctx.memory.execution | Until execution ends | This execution only | No | Step state, intermediate results |
ctx.memory.session | Hours to days | Same user session | No | Conversation context, user preferences |
ctx.memory.persistent | Until explicitly deleted | Same user, any agent | Yes | Knowledge base, long-term user state |
ctx.memory.suite | Until suite completes | All agents in the suite | Yes | Cross-agent data sharing in workflows |
Key-Value Storage
All four scopes support key-value operations. Values are JSON-serialized automatically.
// Key-value storageawait ctx.memory.execution.set('step', 'extracting');const step = await ctx.memory.execution.get('step'); // 'extracting'
// Store complex objects (automatically serialized)await ctx.memory.persistent.set('user_preferences', { language: 'en', timezone: 'America/New_York', notifications: true,});
const prefs = await ctx.memory.persistent.get('user_preferences');// { language: 'en', timezone: 'America/New_York', notifications: true }KeyValueStore API
| Method | Returns | Description |
|---|---|---|
get(key) | Promise<T | null> | Read a value. Returns null if not found. |
set(key, value) | Promise<void> | Write a value. Overwrites existing. |
delete(key) | Promise<void> | Remove a key. |
has(key) | Promise<boolean> | Check if a key exists. |
list(prefix?) | Promise<string[]> | List keys, optionally filtered by prefix. |
Vector Store
The persistent and suite scopes also include a vector store for semantic search. Use ctx.llm.embed() to generate vectors, then store and search them.
// Vector storage for semantic search (persistent and suite scopes)const embedding = await ctx.llm.embed('Invoice processing workflow');
// Store with metadataawait ctx.memory.persistent.store(embedding.vector, { key: 'kb/invoice-workflow', metadata: { category: 'finance', source: 'internal-kb', updatedAt: Date.now(), },});
// Semantic searchconst results = await ctx.memory.persistent.search( (await ctx.llm.embed(userQuery)).vector, { limit: 5, minScore: 0.75 });
for (const result of results) { console.log(result.key, 'score:', result.score); console.log(result.metadata);}VectorStore API
| Method | Returns | Description |
|---|---|---|
store(vector, options) | Promise<string> | Store a vector with key and metadata. Returns the storage ID. |
search(vector, options) | Promise<VectorSearchResult[]> | Find similar vectors. Options: limit, minScore. |
delete(key) | Promise<void> | Remove a stored vector by key. |
Sharing Data Across Agents
ctx.memory.suite is the recommended way to pass large data between agents in a workflow — avoids serializing large payloads through function arguments.
// Suite memory — shared across all agents in the same workflow// Agent A (web-researcher) stores research resultsawait ctx.memory.suite.set('research_results', researchData);
// Agent B (report-generator) in the same suite reads themconst research = await ctx.memory.suite.get('research_results');
// Useful for: passing large data between agents without duplicating in function args,// building shared context as a multi-agent workflow progressesTracking Execution Progress
// Track multi-step progress in execution memoryawait ctx.memory.execution.set('progress', { step: 1, total: 5, status: 'processing' });
// Later in the same executionconst progress = await ctx.memory.execution.get('progress');await ctx.memory.execution.set('progress', { ...progress, step: 2 });
// When execution ends, this is automatically cleaned up — no manual delete neededIn the wild
Reference agents that demonstrate ctx.memory in production.
Vector store (embed + search)semantic-search
Index documents with ctx.llm.embed(), search with ctx.memory.persistent.search(). The RAG foundation.
Cache for deduplicationjob-lifecycle-manager
ctx.cache.get() to skip already-queued jobs, ctx.cache.del() on cancellation.
Cache for diff detectioncompetitive-intelligence
Cache previous results to detect what changed since the last monitoring run.