Last updated

Quick Start Guide

Welcome to Papr Memory! This guide will get you up and running with adding memory to your experience in just 15 minutes. Whether you're building an AI assistant, knowledge management system, or any AI app that needs intelligent memory capabilities, you're in the right place.

What You'll Learn

By the end of this guide, you'll know how to:

  • Set up Papr Memory in your project
  • Add memories to your knowledge base
  • Retrieve memories using semantic + graph-based search

Get your API Key

Create a free account then get your API Key from settings.

Installation

# No installation needed for curl
# Just make sure curl is installed on your system

Authentication

Add PAPR_MEMORY_API_KEY to your .env file, then use it to authenticate:

# Set your API key as an environment variable
export PAPR_MEMORY_API_KEY='your_api_key_here'

Creating Users

Before adding memories, create users to associate with your memories. This enables:

  • User-specific memory storage and retrieval
  • Access control for memories
  • Organizing memories by user
  • Sharing of memories between users
# Create a user
curl -X POST https://memory.papr.ai/v1/user \
  -H "X-API-Key: $PAPR_MEMORY_API_KEY" \
  -H "Content-Type: application/json" \
  -H "X-Client-Type: curl" \
  -d '{
    "external_id": "user123", # Your application's user identifier
    "email": "user@example.com", # Optional
    "metadata": {
      "name": "John Doe", # Optional
      "role": "developer" # Optional
    }
  }'

User ID Storage Best Practices

Store Papr-generated user IDs securely for future operations:

  1. Database Storage: Store the Papr user_id alongside your application's user records
  2. Session Storage: For web applications, store in a secure session
  3. Environment Variables: For testing, you can use environment variables
# Example: Storing user ID in your database
def save_papr_user_id(app_user_id, papr_user_id):
    # Your database code here
    db.users.update_one(
        {"id": app_user_id},  # Your application's internal user ID
        {"$set": {"papr_user_id": papr_user_id}}  # The Papr-generated ID (e.g., "usr_abc123")
    )
    
# Example: Retrieving user ID from your database
def get_papr_user_id(app_user_id):
    user = db.users.find_one({"id": app_user_id})
    return user.get("papr_user_id")  # Returns the Papr-generated ID

Adding Memories

Add a new memory to your knowledge base, using the Papr-generated user ID for association:

curl -X POST https://memory.papr.ai/v1/memory \
  -H "X-API-Key: $PAPR_MEMORY_API_KEY" \
  -H "Content-Type: application/json" \
  -H "X-Client-Type: curl" \
  -d '{
    "content": "Meeting notes from the product planning session",
    "type": "text",
    "metadata": {
      "user_id": "usr_abc123",  // Papr-generated user ID from user creation
      "createdAt": "2024-03-21T10:00:00Z"
    }
  }'

Searching Memories

Search through memories using natural language and the Papr-generated user ID to retrieve user-specific memories:

curl -X POST https://memory.papr.ai/v1/memory/search \
  -H "X-API-Key: $PAPR_MEMORY_API_KEY" \
  -H "Content-Type: application/json" \
  -H "Accept-Encoding: gzip" \
  -H "X-Client-Type: curl" \
  -d '{
    "query": "What are the key points from our recent product planning?",
    "metadata": {
      "user_id": "usr_abc123"  // Papr-generated user ID from user creation
    }
  }'

You can choose whether to search memories for a specific user or across all accessible memories:

# Search only for a specific user's memories (using the Papr-generated ID)
user_specific_results = client.memory.search(
    query="product planning",
    metadata={"user_id": user_id}  # The Papr-generated user ID
)

# Search across all accessible memories
global_results = client.memory.search(
    query="product planning"
    # No user_id in metadata means search all accessible memories
)

Getting a Specific Memory

Retrieve a specific memory by its ID to verify it was added correctly:

curl -X GET https://memory.papr.ai/v1/memory/mem_abc123 \
  -H "X-API-Key: $PAPR_MEMORY_API_KEY" \
  -H "Content-Type: application/json" \
  -H "X-Client-Type: curl"

ACL and Memory Permissions

Note the acl field in the response, which shows that the memory is accessible only to the user who created it. This is automatically set based on the Papr-generated user_id in the metadata when creating the memory.

Papr as an Agentic Tool

Use Papr Memory directly as a tool in your AI applications for advanced memory capabilities:

import os
import aiohttp
from typing import Optional, Dict, Any

# Initialize with your API key from .env
PAPR_API_KEY = os.environ.get("PAPR_MEMORY_API_KEY")

async def search_papr_memory(query: str, user_id: Optional[str] = None):
    """Search through Papr memory with a natural language query."""
    headers = {
        "X-API-Key": PAPR_API_KEY,
        "Content-Type": "application/json",
        "Accept-Encoding": "gzip",
        "X-Client-Type": "agent"
    }
    
    payload = {"query": query}
    if user_id:
        payload["metadata"] = {"user_id": user_id}  # Papr-generated user ID
    
    async with aiohttp.ClientSession() as session:
        async with session.post(
            "https://memory.papr.ai/v1/memory/search", 
            headers=headers, 
            json=payload
        ) as response:
            return await response.json()

async def add_papr_memory(content: str, user_id: Optional[str] = None, metadata: Optional[Dict[str, Any]] = None, memory_type: str = "text"):
    """Add a new memory to Papr memory system."""
    headers = {
        "X-API-Key": PAPR_API_KEY,
        "Content-Type": "application/json",
        "X-Client-Type": "agent"
    }
    
    if metadata is None:
        metadata = {}
        
    if user_id:
        metadata["user_id"] = user_id  # Papr-generated user ID
    
    payload = {
        "content": content,
        "type": memory_type,
        "metadata": metadata
    }
    
    async with aiohttp.ClientSession() as session:
        async with session.post(
            "https://memory.papr.ai/v1/memory", 
            headers=headers, 
            json=payload
        ) as response:
            return await response.json()

# Example usage with any LLM framework
async def agent_with_memory(user_query: str, user_id: str):
    # Retrieve relevant context from memory using Papr-generated user ID
    memory_response = await search_papr_memory(user_query, user_id)
    memories = memory_response.get("data", {}).get("memories", [])
    
    # Create context from memories
    context = ""
    if memories:
        context = "Relevant information from memory:\n"
        for memory in memories[:3]:  # Top 3 memories
            context += f"- {memory['content']}\n"
    
    # Use context with your LLM of choice
    llm_response = await your_llm_call(f"{context}\n\nUser query: {user_query}")
    
    # Store the interaction in memory
    await add_papr_memory(
        content=f"User question: {user_query}\nAgent response: {llm_response}",
        user_id=user_id,  # Papr-generated user ID
        metadata={"conversation_type": "agent_interaction"}
    )
    
    return llm_response

# Example usage
response = await search_papr_memory("Find information about our latest product meeting", "usr_abc123")  # Papr-generated user ID
print(f"Found {len(response.get('data', {}).get('memories', []))} memories")

Next Steps

Congratulations! You've learned the basics of working with Papr Memory, including how to create users and associate memories with them. Here's what to explore next:

  • Core Concepts - Learn about memory types, embeddings, and knowledge graphs
  • Guides:
  • API Reference - View the complete API documentation
  • Tutorials - Build complete projects with our step-by-step tutorials
  • SDKs and Tools - Get started with the Python and Typscript SDKs, or use Papr with an AI agent or langchain via a tool call or MCP server.