Semantic memory layer for AI applications with vector storage and LLM-based extraction
Project description
Longterm AI Memory
A semantic longeterm AI memory layer for Agentic AI applications that remembers context across conversations.
What It Does
Most AI assistants forget everything between sessions. This SDK solves that by extracting factual information from conversations, storing it as searchable vector embeddings, and retrieving relevant context when needed.
Your AI can reference things users mentioned weeks ago without them repeating themselves.
Example:
from longterm_ai_memory import Memory
memory = Memory(user_id="user-123")
# Store information
memory.add("My name is Sarah and I work at Google")
memory.add("I'm allergic to shellfish")
# Search later
results = memory.search("what are my dietary restrictions?")
# Returns: "User is allergic to shellfish"
Installation
pip install longterm_ai_memory
Requirements:
- Python 3.8+
- Pinecone account (free tier available)
- OpenRouter API key (for cloud LLM) OR Ollama installed (for local LLM)
Quick Start
1. Set Up Environment
Create a .env file:
PINECONE_API_KEY=your_pinecone_key_here
OPENROUTER_API_KEY=your_openrouter_key # only if using cloud LLM
2. Basic Usage
from longterm_ai_memory import Memory
import os
from dotenv import load_dotenv
load_dotenv()
# Initialize with cloud LLM (OpenRouter)
memory = Memory(
user_id="demo-user",
pinecone_api_key=os.getenv("PINECONE_API_KEY"),
openrouter_api_key=os.getenv("OPENROUTER_API_KEY"),
use_local_llm=False
)
# OR initialize with local LLM (Ollama - free)
memory = Memory(
user_id="demo-user",
pinecone_api_key=os.getenv("PINECONE_API_KEY"),
use_local_llm=True
)
# Add memories
memory.add("My name is Alex and I work at Microsoft")
memory.add("I love playing tennis on weekends")
# Search memories
results = memory.search("what's my name?")
for result in results:
print(f"{result['metadata']['memory']} (score: {result['score']:.2f})")
# Get all memories
all_memories = memory.get_all()
# Delete all memories
memory.delete_all()
How It Works
User Message → LLM Extraction → Vector Embedding → Pinecone Storage
↓ ↓ ↓
Filters noise, multilingual-e5 Namespaced
converts to 3rd person by user_id
Search Query → Vector Embedding → Semantic Search → Ranked Results
Key Features:
- Automatic fact extraction - LLM converts conversations to factual statements
- Semantic search - Find memories by meaning, not just keywords
- Multi-tenant - Each user gets isolated storage namespace
- Noise filtering - Ignores "okay", "cool", conversational filler
- Local or cloud LLM - Use free Ollama or pay-per-use OpenRouter
- Category auto-assignment - Memories tagged with relevant categories
API Reference
Initialization
Memory(
user_id: str, # Required: unique user identifier
pinecone_api_key: str, # Required: Pinecone API key
openrouter_api_key: str = None, # Required if use_local_llm=False
use_local_llm: bool = True, # True=Ollama, False=OpenRouter
local_llm_model: str = "phi3:mini", # Ollama model name
skip_health_check: bool = False # Skip startup validation
)
add(user_message, categories=None)
Store a new memory from user message.
result = memory.add("My favorite food is sushi")
# Returns: {"id": "...", "memory": "User's favorite food is sushi", "metadata": {...}}
# Noise filtered → returns None
result = memory.add("okay cool") # None
Parameters:
user_message(str): User's message to extract memory fromcategories(list, optional): Manual category override (not recommended)
Returns: Dict with memory data or None if no factual content found.
search(query, top_k=5, filter=None)
Search for relevant memories using semantic similarity.
results = memory.search("what do I like to eat?", top_k=3)
# With category filter
results = memory.search("work info", filter={"categories": "work"})
Parameters:
query(str): Natural language search querytop_k(int): Maximum results to return (1-20, default: 5)filter(dict, optional): Metadata filter
Returns: List of dicts with id, score, and metadata fields, sorted by relevance.
get_all(filter=None)
Retrieve all memories for the current user.
all_memories = memory.get_all()
# With filter
work_memories = memory.get_all(filter={"categories": "work"})
Returns: List of all memories (up to 10,000).
list(limit=100)
Quick way to get recent memories.
recent = memory.list(limit=20)
delete_all()
Delete all memories for the current user.
success = memory.delete_all() # Returns True if successful
Warning: No undo. Use with caution.
Local LLM Setup (Free Alternative)
Install Ollama for free local LLM inference:
# macOS/Linux
curl -fsSL https://ollama.com/install.sh | sh
# Pull a model
ollama pull phi3:mini
# Start server (runs in background)
ollama serve
Supported models:
phi3:mini(recommended, 3.8GB)gemma2:2b(lightweight, 1.6GB)llama3:8b(more capable, 4.7GB)
Then initialize with use_local_llm=True.
Configuration
Customize behavior by modifying config.py:
# Search similarity threshold (0.0-1.0)
SEARCH_CONFIG = {
"similarity_threshold": 0.7, # Higher = stricter matching
"default_top_k": 5
}
# Memory categories (auto-assigned by LLM)
MEMORY_CATEGORIES = [
"work", "personal", "health", "preferences",
"family", "education", "hobbies", "misc"
]
# LLM models
LOCAL_LLM_CONFIG = {
"extraction_model": "phi3:mini",
"base_url": "http://localhost:11434"
}
OPENROUTER_CONFIG = {
"extraction_model": "google/gemma-2-9b-it:free"
}
Use Cases
Chatbot with Memory
def chatbot_with_memory(user_message):
# 1. Search for relevant context
context = memory.search(user_message, top_k=3)
# 2. Build prompt with context
context_text = " | ".join([m['metadata']['memory'] for m in context])
prompt = f"Context: {context_text}\n\nUser: {user_message}"
# 3. Generate response with your LLM
response = your_llm.generate(prompt)
# 4. Store new information
memory.add(user_message)
return response
Personal Assistant
# Store user preferences
memory.add("I prefer emails over phone calls")
memory.add("My meetings are usually in the mornings")
# Later, retrieve context for scheduling
prefs = memory.search("communication and scheduling preferences")
Customer Support
# Store customer information
memory.add("Customer is on enterprise plan")
memory.add("Customer's primary use case is data analytics")
# Retrieve during support conversations
customer_info = memory.search("plan and use case")
Architecture
Components:
- Memory (core) - Main orchestrator, handles all operations
- MemoryExtractor - LLM-based extraction (Ollama or OpenRouter)
- VectorStore - Pinecone backend with namespace isolation
- EmbeddingProvider - Pinecone inference API for embeddings
- MetadataGenerator - Temporal + categorical metadata
Storage:
- Each user gets isolated namespace in Pinecone
- Embeddings: 1024-dimensional vectors (multilingual-e5-large)
- Metadata: categories, timestamps, temporal fields (day, month, quarter, etc.)
Advanced Features
Time-Based Filtering
from datetime import datetime
# Get memories from this year
all_memories = memory.get_all()
this_year = datetime.now().year
recent = [m for m in all_memories if m['metadata']['year'] == this_year]
# Weekend memories
weekend = [m for m in all_memories if m['metadata']['is_weekend']]
Batch Operations
messages = [
"I graduated from Stanford in 2020",
"My favorite food is sushi",
"I have two cats named Luna and Mochi"
]
for msg in messages:
result = memory.add(msg)
if result:
print(f"Stored: {result['memory']}")
Error Handling
from longterm_ai_memory import ValidationError, MemoryError
try:
result = memory.add(user_message)
except ValidationError as e:
print(f"Invalid input: {e}")
except MemoryError as e:
print(f"Operation failed: {e}")
Limitations
- Memory updates require delete + add (no direct update operation)
- Conversation threading not implemented
- Storage backend limited to Pinecone (no ChromaDB/Qdrant support yet)
- Batch operations not optimized for high-volume scenarios
- Maximum 10,000 memories per user via
get_all()(pagination needed for more)
Roadmap
Planned improvements:
- Additional storage backends (ChromaDB, Qdrant, Weaviate)
- Conversation context tracking
- Enhanced category inference
- Memory importance scoring
- Temporal decay for older memories
Contributing
Contributions welcome! Areas needing work:
- Additional storage backends
- Better category inference
- Memory deduplication
- Conversation threading
- Performance optimization
License
MIT License - See LICENSE for details.
Links
- GitHub: github.com/omkar1344patil/longterm-ai-memory
- PyPI: pypi.org/project/longterm-ai-memory
- Issues: Report bugs or request features
Questions or feedback? Open an issue on GitHub or reach out on LinkedIn.
Project details
Release history Release notifications | RSS feed
Download files
Download the file for your platform. If you're not sure which to choose, learn more about installing packages.
Source Distribution
Built Distribution
Filter files by name, interpreter, ABI, and platform.
If you're not sure about the file name format, learn more about wheel file names.
Copy a direct link to the current filters
File details
Details for the file longterm_ai_memory-0.1.2.tar.gz.
File metadata
- Download URL: longterm_ai_memory-0.1.2.tar.gz
- Upload date:
- Size: 21.5 kB
- Tags: Source
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.2.0 CPython/3.13.11
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
3d295a06843fbb6e08310157425f3d9b25be5a7f47b39479e3a3aeac97c37a2c
|
|
| MD5 |
a243e5a166fc9c7d51d6ca1f90ca16ab
|
|
| BLAKE2b-256 |
1d2e16fd5c28ebdcde23372e03117af33aeaeecf4ba58dfb2ef93b6b0a26c586
|
File details
Details for the file longterm_ai_memory-0.1.2-py3-none-any.whl.
File metadata
- Download URL: longterm_ai_memory-0.1.2-py3-none-any.whl
- Upload date:
- Size: 22.7 kB
- Tags: Python 3
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.2.0 CPython/3.13.11
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
7d74e65cb7377c83dc5336f928c47b794213a4cd978813dca07c5868e52a2e23
|
|
| MD5 |
61bc5994b7f8384a6735924289b44e0c
|
|
| BLAKE2b-256 |
7aed2f5d46c9818116759cab6345e612e8a5c69169508aa6351d3a93aa559a45
|