Two-call integration
Add per-user memory to your SaaS copilot in two API calls.
Persistent memory without rebuilding your AI pipeline. Save what matters, recall the right context, inject into your prompt, and keep using your existing model stack.
Your AI app forgets users between sessions. Fix it with POST /v1/memories (save what you learn) and POST /v1/search or POST /v1/context (recall before the next reply). Use the same owner_id as your SaaS app's logged-in user ID.
For stack-specific copy-paste (OpenAI, REST, MCP), see Integration recipes.
Base URL: https://api.memorynode.ai (or your self-hosted Worker URL).
Concepts you need
| Concept | What it means |
|---|---|
| Workspace | Your MemoryNode project. One API key belongs to one workspace. Create keys in the console under App connection. |
| API key | Authorization: Bearer mn_live_… (or x-api-key: mn_live_…). Required on every product route. |
owner_id | Your SaaS app's user ID — the same string you use for user_id in the API body. Session 1 and session 2 must use the same value or recall looks empty. |
POST /v1/memories | Saves what your copilot learned about a user (preferences, habits, account facts). |
POST /v1/search | Recalls ranked memory hits before you generate the next AI reply. |
POST /v1/context | Same recall pipeline, plus assembled context_text for your LLM (recommended for prompts). |
Playground default is default-user. In production, replace it with your real user ID.
Authentication
Authorization: Bearer mn_live_…your_key…
Content-Type: application/json
Every response includes x-request-id — log it for support and debugging.
SaaS copilot example
Session 1 — user tells your copilot how they work:
"I prefer weekly email digests and dark mode on the dashboard."
Session 2 — user asks a different question:
"How should the dashboard feel for this user?"
MemoryNode recalls the preference. Your LLM answers without re-asking.
cURL
export MEMORYNODE_API_KEY="mn_live_..."
export OWNER_ID="user_42" # your SaaS user id
# Session 1 — remember
curl -sS -X POST "https://api.memorynode.ai/v1/memories" \
-H "Authorization: Bearer $MEMORYNODE_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"user_id": "'"$OWNER_ID"'",
"text": "User prefers weekly email digests and dark mode on the dashboard.",
"extract": false
}'
# Session 2 — recall before the reply
curl -sS -X POST "https://api.memorynode.ai/v1/search" \
-H "Authorization: Bearer $MEMORYNODE_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"user_id": "'"$OWNER_ID"'",
"query": "How should the dashboard feel for this user?",
"top_k": 5,
"namespace": "default",
"search_mode": "hybrid"
}'
Save the x-request-id header from the search response.
Node / TypeScript
npm install @memorynodeai/sdk
export MEMORYNODE_API_KEY="mn_live_..."
import { MemoryNode } from "@memorynodeai/sdk";
const ownerId = "user_42"; // same as your SaaS logged-in user id
const memory = new MemoryNode(process.env.MEMORYNODE_API_KEY!);
// Session 1
await memory.remember(
"User prefers weekly email digests and dark mode on the dashboard.",
{ ownerId },
);
// Session 2
const { results } = await memory.recall("How should the dashboard feel for this user?", {
ownerId,
topK: 5,
explain: true,
});
console.log(results?.[0]?.text);
Runnable: examples/sdk-quickstart
Python
pip install httpx
export MEMORYNODE_API_KEY="mn_live_..."
export OWNER_ID="user_42"
import os
import httpx
BASE = "https://api.memorynode.ai"
KEY = os.environ["MEMORYNODE_API_KEY"]
OWNER = os.environ.get("OWNER_ID", "user_42")
headers = {"Authorization": f"Bearer {KEY}", "content-type": "application/json"}
with httpx.Client(base_url=BASE, headers=headers, timeout=30.0) as client:
client.post(
"/v1/memories",
json={
"user_id": OWNER,
"text": "User prefers weekly email digests and dark mode on the dashboard.",
"extract": False,
},
).raise_for_status()
hits = client.post(
"/v1/search",
json={
"user_id": OWNER,
"query": "How should the dashboard feel for this user?",
"top_k": 5,
"namespace": "default",
"search_mode": "hybrid",
},
).raise_for_status().json()
print(hits.get("results", [{}])[0].get("text"))
Wire it in your app (save → recall → inject)
- Save — after each user message (or session end), call
POST /v1/memorieswith facts your app should remember. - Recall — before each AI reply, call
POST /v1/contextwith the current question asquery(orPOST /v1/searchif you assemble the prompt yourself). - Inject — merge
context_text(or joined search hit texts) into your LLM system or user message. Your OpenAI / Anthropic / Vercel AI / LangChain code stays the same. - Keep your stack — MemoryNode is a memory layer; you still call your existing model provider.
- Keep
user_id/owner_ididentical to your auth user id across sessions.
Context pack (recommended for prompts)
curl -sS -X POST "https://api.memorynode.ai/v1/context" \
-H "Authorization: Bearer $MEMORYNODE_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"user_id": "'"$OWNER_ID"'",
"query": "How should the dashboard feel for this user?",
"top_k": 8,
"namespace": "default"
}'
Use the returned context_text in your system prompt. SDK: memory.contextFor(query, { ownerId }).
Runnable REST example: examples/integrations/rest-node.
Prove recall in the console Playground first — save one memory, then Build context. See START_HERE.
Common errors
| HTTP | Typical error.code | Fix |
|---|---|---|
| 401 | UNAUTHORIZED | Missing or invalid API key. |
| 400 | BAD_REQUEST | Validation failed — check user_id, text, query. |
| 402 | daily_cap_exceeded, monthly_cap_exceeded, ENTITLEMENT_REQUIRED, trial expired | Upgrade via console billing (PayU INR) or wait for cap reset. |
| 429 | rate_limited | Back off and retry; see plan RPM limits. |
Full reference: API_USAGE.md · OpenAPI
Not needed for first recall
Skip these until you have working write + search in production:
- MCP — builder tools only (Cursor/Claude); ship with REST/SDK first (MCP_SERVER.md)
- Brain / rerank tuning — defaults work for first recall
- Eval sets — add after you ship
Next reads
- START_HERE — Playground-first activation path
- INTEGRATION_RECIPES — REST, OpenAI, MCP, stack patterns
- INTEGRATION — advanced capabilities (dedupe, lifecycle, feedback)
- TROUBLESHOOTING — empty search, auth, 402
- Pricing — trial and PayU (INR)