Migrating to Sonzai
Bring users, chat history, memories, and documents from your existing AI stack into Sonzai's memory constellation. One overview page plus a tutorial for every common source system.
Why migrate
Most memory systems store strings. Sonzai builds a memory constellation: every incoming piece of content is passed through a fact-extraction pipeline, deduplicated against what the agent already knows, linked into a graph, and surfaced automatically during future conversations. Per-user mood, relationship state, and proactive wakeups all key off that constellation.
If you're coming from a raw transcript store, a RAG index, or a memory-as-a-service vendor, you get three things by migrating:
- Automatic fact extraction + supersession — no more manually curating which memories matter.
- Per-user state — mood, relationship depth, goals, and habits tracked separately for every user of the same agent.
- One import, many agents — migrated users are usable by any agent in the project, not tied to a single thread.
The import surfaces
Sonzai exposes three endpoints for bringing data in. Pick based on shape:
| You have... | Use | Endpoint |
|---|---|---|
| Many users at once (chat histories, CRM contacts, memory exports) | Batch import | POST /api/v1/agents/{agentId}/users/import |
| One user with rich metadata + content | Prime user | POST /api/v1/agents/{agentId}/users/{userId}/prime |
| More content for a user already in Sonzai | Add content | POST /api/v1/agents/{agentId}/users/{userId}/content |
| Documents (PDF / DOCX / MD / TXT) for the knowledge base | Upload document | POST /api/v1/projects/{projectId}/knowledge/documents |
Full field-level reference for the priming endpoints lives in API → Priming. The tutorials below show how to shape data from each source system into these endpoints.
How the pipeline works
Every call to an import endpoint is asynchronous and returns a job_id.
Your data
|
v
+----------------------+
| Metadata fields | --> facts generated synchronously (fast)
+----------------------+
+----------------------+ NATS queue
| Content blocks | ---------------> LLM fact extraction
+----------------------+ |
v
Memory constellation
(dedup + supersession)
- Metadata (
display_name,company,title,email,phone,custom) is converted into facts on the spot. The response tells you how many. - Content blocks are queued to NATS; a worker runs LLM extraction against them and merges the results into the user's memory tree.
- Job status is pollable at
GET /api/v1/agents/{agentId}/users/import/{jobId}for batch imports (or.../users/{userId}/prime/{jobId}for single-user primes). Whenstatusiscompleted, extraction is done.
This means a big batch import returns quickly (HTTP 202 Accepted) and then keeps processing in the background.
Content block shape
Every content-carrying payload uses the same block shape:
{ "type": "chat_transcript", "body": "User: Hi\nAgent: Hey Mia, how's the hiking been?" }type— a free-form label. Common values:"text","chat_transcript","note","bio". The extractor uses the label as a hint but doesn't reject unknown values.body— raw text. Split long transcripts across multiple blocks if you prefer, or pack one session per block. Either works.
The source field
All three priming endpoints accept an optional top-level source string. It is purely provenance metadata — the backend stores it on the import job and the resulting facts. It does not change behaviour. Pick whatever is meaningful to you:
{ "source": "openai_assistants", "users": [ ... ] }Suggested values used throughout the tutorials below: openai_assistants, zep, mem0, letta, langchain, character_ai, replika, custom_json, crm.
Pick your migration path
OpenAI Assistants
Threads + messages → batch import with chat_transcript blocks
Zep (getzep)
User memory + session transcripts → facts + transcripts
Mem0
Per-user memory strings → text blocks
Letta / MemGPT
Core + archival memory → metadata + content
LangChain memory
ConversationBufferMemory / ChatMessageHistory → transcripts
Character.AI / Replika
Companion exports → agent + users + chat history
Custom JSON
Homegrown chat stores → generic batch import
CRM / CSV
Structured contact data → deterministic facts
Knowledge base documents
PDFs, DOCX, MD, TXT → knowledge graph
A minimal end-to-end example
If you just want to see the whole loop once before diving into a source-specific guide:
import { Sonzai } from "@sonzai-labs/agents";
const client = new Sonzai({ apiKey: process.env.SONZAI_API_KEY! });
const AGENT_ID = "agent_abc";
// 1. Import
const job = await client.agents.priming.batchImport(AGENT_ID, {
source: "custom_json",
users: [
{
user_id: "user_123",
display_name: "Mia Tanaka",
metadata: { email: "[email protected]", company: "Acme" },
content: [
{ type: "chat_transcript", body: "User: I'm allergic to peanuts.\nAgent: Noted." },
],
},
],
});
console.log(job.job_id, job.total_users, job.facts_created);
// 2. Poll for completion
let status = await client.agents.priming.getImportStatus(AGENT_ID, job.job_id);
while (status.status !== "completed" && status.status !== "failed") {
await new Promise(r => setTimeout(r, 2000));
status = await client.agents.priming.getImportStatus(AGENT_ID, job.job_id);
}
console.log(status);Once the job completes, call GET /api/v1/agents/{agentId}/users to confirm the user is there with the extracted facts attached.
What happens to the data
After a successful import you have, per user:
- An entry in the agent's user list (
GET /api/v1/agents/{agentId}/users) - A priming metadata record (
GET /api/v1/agents/{agentId}/users/{userId}/metadata) - Extracted facts in the memory constellation (
GET /api/v1/agents/{agentId}/memory/facts?user_id=...) - An initial mood state derived from the agent's Big5 baseline
- Read access to the agent granted automatically
You can now chat with the agent as that user and every extracted fact is available for retrieval.
Tool Integration for BYO-LLM
When using standalone memory mode, your LLM handles chat generation but may need to search knowledge and memory on demand. Sonzai exposes tool schemas compatible with OpenAI function calling, so you can wire them into any agent framework.
From OpenAI Assistants
Migrate threads and messages from the OpenAI Assistants API into Sonzai. One thread per user, full message history preserved as chat transcripts.