Memory Management API
🧠 Intelligent Memory System
The Memory Management API provides access to Quantbot's Neo4j-based memory system powered by graphiti-core. This system stores conversation history, extracts entities, and enables contextual memory retrieval for AI agents.
Base URL
All memory management endpoints are prefixed with:
Authentication
All memory endpoints require authentication. Include the Bearer token in the Authorization header:
Overview
The Memory API is divided into two main categories:
Ingestion Endpoints (/ingest/
)
- Store messages and entities in memory
- Manage conversation episodes
- Delete memory data
Retrieval Endpoints (/retrieve/
)
- Search memories using semantic similarity
- Retrieve conversation episodes
- Get contextual memory for conversations
Data Models
Message
{
"content": "How is Apple stock performing today?",
"uuid": "msg_123e4567-e89b-12d3-a456-426614174000",
"name": "User Question",
"role_type": "user",
"role": "John Doe",
"timestamp": "2025-01-15T10:30:00Z",
"source_description": "Chat interface"
}
FactResult
{
"uuid": "fact_123e4567-e89b-12d3-a456-426614174000",
"name": "Apple Stock Analysis",
"fact": "Apple (AAPL) closed at $185.25, up 2.1% from previous session",
"valid_at": "2025-01-15T10:30:00Z",
"invalid_at": null,
"created_at": "2025-01-15T10:30:00Z",
"expired_at": null
}
Result
Ingestion Endpoints
Add Messages to Memory
Store conversation messages in the memory system for later retrieval.
Request Body
{
"group_id": "user_123",
"messages": [
{
"content": "What's the latest news on Tesla stock?",
"uuid": "msg_001",
"name": "Tesla Inquiry",
"role_type": "user",
"role": "John Doe",
"timestamp": "2025-01-15T10:30:00Z",
"source_description": "Chat interface"
},
{
"content": "Tesla (TSLA) is currently trading at $248.50, up 1.8% today. Recent news includes their Q4 delivery numbers exceeding expectations.",
"uuid": "msg_002",
"name": "Tesla Analysis",
"role_type": "assistant",
"role": "Market Analyst",
"timestamp": "2025-01-15T10:31:00Z",
"source_description": "AI Agent Response"
}
]
}
Response
Status Code: 202 Accepted
Add Entity Node
Create a new entity node in the memory graph.
Request Body
{
"uuid": "entity_tesla_stock",
"group_id": "user_123",
"name": "Tesla Stock (TSLA)",
"summary": "Electric vehicle company stock with high volatility and growth potential"
}
Response
Status Code: 201 Created
{
"uuid": "entity_tesla_stock",
"group_id": "user_123",
"name": "Tesla Stock (TSLA)",
"summary": "Electric vehicle company stock with high volatility and growth potential",
"created_at": "2025-01-15T10:30:00Z"
}
Delete Entity Edge
Remove a specific entity edge from the memory graph.
Path Parameters
Parameter | Type | Description |
---|---|---|
uuid |
string | UUID of the entity edge to delete |
Response
Status Code: 200 OK
Delete User Group Memory
Delete all memory data for a specific user group.
Path Parameters
Parameter | Type | Description |
---|---|---|
group_id |
string | Group ID to delete all memory for |
Response
Status Code: 200 OK
Delete Episode
Remove a specific conversation episode from memory.
Path Parameters
Parameter | Type | Description |
---|---|---|
uuid |
string | UUID of the episode to delete |
Response
Status Code: 200 OK
Clear All Data (Admin Only)
⚠️ DANGER: This endpoint clears ALL memory data from the system.
Authentication Required
Note: Only superuser accounts can access this endpoint.
Response
Status Code: 200 OK
Retrieval Endpoints
Search Memories
Search for relevant memories using semantic similarity.
Request Body
Response
Status Code: 200 OK
{
"facts": [
{
"uuid": "fact_001",
"name": "Tesla Stock Analysis",
"fact": "Tesla (TSLA) closed at $248.50, up 1.8% today",
"valid_at": "2025-01-15T10:30:00Z",
"invalid_at": null,
"created_at": "2025-01-15T10:30:00Z",
"expired_at": null
},
{
"uuid": "fact_002",
"name": "Tesla Q4 Deliveries",
"fact": "Tesla reported Q4 deliveries of 484,507 vehicles, exceeding analyst expectations",
"valid_at": "2025-01-15T09:00:00Z",
"invalid_at": null,
"created_at": "2025-01-15T09:00:00Z",
"expired_at": null
}
]
}
Get Entity Edge
Retrieve a specific entity edge by UUID.
Path Parameters
Parameter | Type | Description |
---|---|---|
uuid |
string | UUID of the entity edge to retrieve |
Response
Status Code: 200 OK
{
"uuid": "edge_001",
"source_uuid": "entity_tesla",
"target_uuid": "entity_stock_market",
"relationship": "TRADES_IN",
"created_at": "2025-01-15T10:30:00Z"
}
Get Episodes
Retrieve recent conversation episodes for a user group.
Path Parameters
Parameter | Type | Description |
---|---|---|
group_id |
string | Group ID to retrieve episodes for |
Query Parameters
Parameter | Type | Required | Description |
---|---|---|---|
last_n |
integer | Yes | Number of recent episodes to retrieve |
Response
Status Code: 200 OK
[
{
"uuid": "episode_001",
"name": "Tesla Stock Discussion",
"created_at": "2025-01-15T10:30:00Z",
"messages": [
{
"content": "What's the latest on Tesla?",
"role_type": "user",
"timestamp": "2025-01-15T10:30:00Z"
}
]
}
]
Get Contextual Memory
Get relevant memory context based on conversation messages.
Request Body
{
"group_id": "user_123",
"max_facts": 10,
"center_node_uuid": "entity_tesla_stock",
"messages": [
{
"content": "How has Tesla been performing lately?",
"role_type": "user",
"role": "John Doe",
"timestamp": "2025-01-15T10:30:00Z"
}
]
}
Response
Status Code: 200 OK
{
"facts": [
{
"uuid": "fact_001",
"name": "Tesla Recent Performance",
"fact": "Tesla stock has gained 15% over the past month following strong delivery numbers",
"valid_at": "2025-01-15T10:30:00Z",
"invalid_at": null,
"created_at": "2025-01-15T10:30:00Z",
"expired_at": null
}
]
}
Memory System Architecture
User Isolation
- Group-based separation: Each user has a unique
group_id
- Data isolation: Users can only access their own memory data
- Privacy protection: No cross-user memory access
Memory Types
- Episodic Memory: Conversation history and temporal context
- Entity Memory: Knowledge about financial instruments, companies, concepts
- Relationship Memory: Connections between entities and facts
Search & Retrieval
- Semantic similarity: Uses embeddings for intelligent memory search
- Temporal awareness: Considers recency and relevance of memories
- Context-aware: Retrieves memories relevant to current conversation
Integration Examples
Python Example
import requests
from datetime import datetime
from typing import List, Dict, Any
class QuantbotMemoryClient:
def __init__(self, base_url: str, access_token: str):
self.base_url = base_url
self.headers = {
"Authorization": f"Bearer {access_token}",
"Content-Type": "application/json"
}
def add_messages(self, group_id: str, messages: List[Dict[str, Any]]) -> Dict[str, Any]:
"""Add messages to memory"""
response = requests.post(
f"{self.base_url}/api/v1/memory/ingest/messages",
headers=self.headers,
json={
"group_id": group_id,
"messages": messages
}
)
response.raise_for_status()
return response.json()
def search_memories(self, group_ids: List[str], query: str, max_facts: int = 10) -> Dict[str, Any]:
"""Search for relevant memories"""
response = requests.post(
f"{self.base_url}/api/v1/memory/retrieve/search",
headers=self.headers,
json={
"group_ids": group_ids,
"query": query,
"max_facts": max_facts
}
)
response.raise_for_status()
return response.json()
def get_contextual_memory(self, group_id: str, messages: List[Dict[str, Any]], max_facts: int = 10) -> Dict[str, Any]:
"""Get contextual memory for conversation"""
response = requests.post(
f"{self.base_url}/api/v1/memory/retrieve/get-memory",
headers=self.headers,
json={
"group_id": group_id,
"max_facts": max_facts,
"center_node_uuid": None,
"messages": messages
}
)
response.raise_for_status()
return response.json()
# Usage
client = QuantbotMemoryClient("http://localhost:8000", "your_access_token")
# Add conversation to memory
messages = [
{
"content": "What's Apple's current stock price?",
"role_type": "user",
"role": "John",
"timestamp": datetime.now().isoformat()
},
{
"content": "Apple (AAPL) is currently trading at $185.25, up 2.1% today.",
"role_type": "assistant",
"role": "Market Analyst",
"timestamp": datetime.now().isoformat()
}
]
result = client.add_messages("user_123", messages)
print("✅ Messages added to memory")
# Search for relevant memories
search_results = client.search_memories(["user_123"], "Apple stock price today")
print(f"Found {len(search_results['facts'])} relevant memories")
# Get contextual memory for new conversation
context = client.get_contextual_memory("user_123", [
{
"content": "How has Apple been performing recently?",
"role_type": "user",
"role": "John",
"timestamp": datetime.now().isoformat()
}
])
print(f"Retrieved {len(context['facts'])} relevant facts for context")
JavaScript/TypeScript Example
interface Message {
content: string;
uuid?: string;
name?: string;
role_type: 'user' | 'assistant' | 'system';
role?: string;
timestamp: string;
source_description?: string;
}
interface FactResult {
uuid: string;
name: string;
fact: string;
valid_at: string | null;
invalid_at: string | null;
created_at: string;
expired_at: string | null;
}
class QuantbotMemoryAPI {
constructor(private baseURL: string, private accessToken: string) {}
private get headers() {
return {
'Authorization': `Bearer ${this.accessToken}`,
'Content-Type': 'application/json'
};
}
async addMessages(groupId: string, messages: Message[]): Promise<{message: string, success: boolean}> {
const response = await fetch(`${this.baseURL}/api/v1/memory/ingest/messages`, {
method: 'POST',
headers: this.headers,
body: JSON.stringify({
group_id: groupId,
messages
})
});
if (!response.ok) {
throw new Error(`Failed to add messages: ${response.statusText}`);
}
return await response.json();
}
async searchMemories(groupIds: string[], query: string, maxFacts: number = 10): Promise<{facts: FactResult[]}> {
const response = await fetch(`${this.baseURL}/api/v1/memory/retrieve/search`, {
method: 'POST',
headers: this.headers,
body: JSON.stringify({
group_ids: groupIds,
query,
max_facts: maxFacts
})
});
if (!response.ok) {
throw new Error(`Failed to search memories: ${response.statusText}`);
}
return await response.json();
}
async getContextualMemory(groupId: string, messages: Message[], maxFacts: number = 10): Promise<{facts: FactResult[]}> {
const response = await fetch(`${this.baseURL}/api/v1/memory/retrieve/get-memory`, {
method: 'POST',
headers: this.headers,
body: JSON.stringify({
group_id: groupId,
max_facts: maxFacts,
center_node_uuid: null,
messages
})
});
if (!response.ok) {
throw new Error(`Failed to get contextual memory: ${response.statusText}`);
}
return await response.json();
}
async deleteGroup(groupId: string): Promise<{message: string, success: boolean}> {
const response = await fetch(`${this.baseURL}/api/v1/memory/ingest/group/${groupId}`, {
method: 'DELETE',
headers: this.headers
});
if (!response.ok) {
throw new Error(`Failed to delete group: ${response.statusText}`);
}
return await response.json();
}
}
// Usage
const memoryAPI = new QuantbotMemoryAPI('http://localhost:8000', 'your_access_token');
// Store conversation in memory
const messages: Message[] = [
{
content: "What's the latest on Tesla stock?",
role_type: "user",
role: "Investor",
timestamp: new Date().toISOString()
}
];
memoryAPI.addMessages('user_123', messages)
.then(result => console.log('✅ Messages stored:', result.message))
.catch(error => console.error('❌ Error:', error));
// Search for relevant information
memoryAPI.searchMemories(['user_123'], 'Tesla stock price performance')
.then(results => console.log(`Found ${results.facts.length} relevant memories`))
.catch(error => console.error('❌ Search error:', error));
Security Considerations
Data Privacy
- All memory data is isolated by user group
- Users cannot access other users' memories
- Admin-only endpoints require superuser privileges
Data Retention
- Configure memory retention policies via environment variables
- Episodes can be manually deleted when no longer needed
- Group deletion removes all user memory data
Performance
- Message ingestion is asynchronous for better performance
- Search operations use efficient vector similarity algorithms
- Caching is implemented for frequently accessed memories
Error Handling
Common Error Responses
401 Unauthorized - Invalid or missing authentication
403 Forbidden - Insufficient permissions (admin endpoints)
404 Not Found - Entity or episode not found
422 Unprocessable Entity - Invalid request data
{
"detail": [
{
"loc": ["body", "group_id"],
"msg": "field required",
"type": "value_error.missing"
}
]
}
Related APIs
- Chat API - Uses memory for context-aware conversations
- Authentication API - Required for all memory operations
- Users API - User management and group ID assignment
Configuration
Environment Variables
The memory system can be configured using these environment variables:
# Neo4j Connection
NEO4J_URI=bolt://neo4j:7687
NEO4J_USER=neo4j
NEO4J_PASSWORD=your_password
# Memory Settings
MEMORY_MAX_EPISODES_PER_USER=10000
MEMORY_RETENTION_DAYS=365
MEMORY_SIMILARITY_THRESHOLD=0.7
DISABLE_MEMORY=false
# Security
MEMORY_ENABLE_ENCRYPTION=true
MEMORY_ISOLATION_STRICT=true
For more details on configuration, see the Installation Guide.