mdb-engine 0.7.3__tar.gz → 0.7.5__tar.gz
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- {mdb_engine-0.7.3/mdb_engine.egg-info → mdb_engine-0.7.5}/PKG-INFO +1 -1
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/__init__.py +1 -1
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/cli/main.py +1 -1
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/core/engine.py +3 -2
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/core/service_initialization.py +5 -4
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/core/types.py +2 -2
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/dependencies.py +3 -3
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/memory/README.md +231 -27
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/memory/__init__.py +9 -0
- mdb_engine-0.7.5/mdb_engine/memory/base.py +224 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/memory/service.py +415 -162
- {mdb_engine-0.7.3 → mdb_engine-0.7.5/mdb_engine.egg-info}/PKG-INFO +1 -1
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine.egg-info/SOURCES.txt +1 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/pyproject.toml +1 -1
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/setup.py +1 -1
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/LICENSE +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/MANIFEST.in +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/README.md +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/README.md +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/auth/ARCHITECTURE.md +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/auth/README.md +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/auth/__init__.py +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/auth/audit.py +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/auth/base.py +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/auth/casbin_factory.py +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/auth/casbin_models.py +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/auth/config_defaults.py +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/auth/config_helpers.py +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/auth/cookie_utils.py +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/auth/csrf.py +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/auth/decorators.py +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/auth/dependencies.py +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/auth/helpers.py +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/auth/integration.py +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/auth/jwt.py +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/auth/middleware.py +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/auth/oso_factory.py +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/auth/provider.py +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/auth/rate_limiter.py +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/auth/restrictions.py +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/auth/session_manager.py +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/auth/shared_middleware.py +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/auth/shared_users.py +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/auth/token_lifecycle.py +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/auth/token_store.py +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/auth/users.py +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/auth/utils.py +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/auth/websocket_sessions.py +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/auth/websocket_tickets.py +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/cli/__init__.py +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/cli/commands/__init__.py +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/cli/commands/generate.py +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/cli/commands/migrate.py +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/cli/commands/show.py +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/cli/commands/validate.py +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/cli/utils.py +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/config.py +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/constants.py +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/core/README.md +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/core/__init__.py +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/core/app_registration.py +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/core/app_secrets.py +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/core/connection.py +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/core/encryption.py +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/core/index_management.py +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/core/manifest.py +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/core/ray_integration.py +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/core/seeding.py +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/database/README.md +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/database/__init__.py +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/database/abstraction.py +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/database/connection.py +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/database/query_validator.py +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/database/resource_limiter.py +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/database/scoped_wrapper.py +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/di/__init__.py +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/di/container.py +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/di/providers.py +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/di/scopes.py +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/embeddings/README.md +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/embeddings/__init__.py +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/embeddings/dependencies.py +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/embeddings/service.py +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/exceptions.py +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/indexes/README.md +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/indexes/__init__.py +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/indexes/helpers.py +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/indexes/manager.py +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/observability/README.md +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/observability/__init__.py +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/observability/health.py +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/observability/logging.py +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/observability/metrics.py +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/repositories/__init__.py +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/repositories/base.py +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/repositories/mongo.py +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/repositories/unit_of_work.py +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/routing/README.md +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/routing/__init__.py +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/routing/websockets.py +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/utils/__init__.py +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine/utils/mongo.py +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine.egg-info/dependency_links.txt +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine.egg-info/entry_points.txt +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine.egg-info/requires.txt +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/mdb_engine.egg-info/top_level.txt +0 -0
- {mdb_engine-0.7.3 → mdb_engine-0.7.5}/setup.cfg +0 -0
|
@@ -910,13 +910,14 @@ class MongoDBEngine:
|
|
|
910
910
|
|
|
911
911
|
def get_memory_service(self, slug: str) -> Any | None:
|
|
912
912
|
"""
|
|
913
|
-
Get
|
|
913
|
+
Get memory service for an app (returns BaseMemoryService instance).
|
|
914
914
|
|
|
915
915
|
Args:
|
|
916
916
|
slug: App slug
|
|
917
917
|
|
|
918
918
|
Returns:
|
|
919
|
-
|
|
919
|
+
BaseMemoryService instance (currently Mem0MemoryService) if memory is enabled
|
|
920
|
+
for this app, None otherwise
|
|
920
921
|
|
|
921
922
|
Example:
|
|
922
923
|
```python
|
|
@@ -63,10 +63,10 @@ class ServiceInitializer:
|
|
|
63
63
|
self, slug: str, memory_config: dict[str, Any] | None
|
|
64
64
|
) -> None:
|
|
65
65
|
"""
|
|
66
|
-
Initialize
|
|
66
|
+
Initialize memory service for an app (defaults to Mem0 implementation).
|
|
67
67
|
|
|
68
68
|
Memory support is OPTIONAL - only processes if dependencies are available.
|
|
69
|
-
|
|
69
|
+
Currently uses Mem0.ai which handles embeddings and LLM via environment variables (.env).
|
|
70
70
|
|
|
71
71
|
Args:
|
|
72
72
|
slug: App slug
|
|
@@ -356,13 +356,14 @@ class ServiceInitializer:
|
|
|
356
356
|
|
|
357
357
|
def get_memory_service(self, slug: str) -> Any | None:
|
|
358
358
|
"""
|
|
359
|
-
Get
|
|
359
|
+
Get memory service for an app (returns BaseMemoryService instance).
|
|
360
360
|
|
|
361
361
|
Args:
|
|
362
362
|
slug: App slug
|
|
363
363
|
|
|
364
364
|
Returns:
|
|
365
|
-
|
|
365
|
+
BaseMemoryService instance (currently Mem0MemoryService) if memory is enabled
|
|
366
|
+
for this app, None otherwise
|
|
366
367
|
"""
|
|
367
368
|
try:
|
|
368
369
|
service = self._memory_services.get(slug)
|
|
@@ -11,9 +11,9 @@ This module is part of MDB_ENGINE - MongoDB Engine.
|
|
|
11
11
|
from typing import TYPE_CHECKING, Any, Literal, TypedDict
|
|
12
12
|
|
|
13
13
|
if TYPE_CHECKING:
|
|
14
|
-
from ..memory import
|
|
14
|
+
from ..memory import BaseMemoryService
|
|
15
15
|
else:
|
|
16
|
-
|
|
16
|
+
BaseMemoryService = Any
|
|
17
17
|
|
|
18
18
|
|
|
19
19
|
# ============================================================================
|
|
@@ -33,7 +33,7 @@ if TYPE_CHECKING:
|
|
|
33
33
|
from .core.engine import MongoDBEngine
|
|
34
34
|
from .database.scoped_wrapper import ScopedMongoWrapper
|
|
35
35
|
from .embeddings.service import EmbeddingService
|
|
36
|
-
from .memory
|
|
36
|
+
from .memory import BaseMemoryService
|
|
37
37
|
|
|
38
38
|
logger = logging.getLogger(__name__)
|
|
39
39
|
|
|
@@ -121,8 +121,8 @@ async def get_embedding_service(request: Request) -> "EmbeddingService":
|
|
|
121
121
|
raise HTTPException(503, f"Failed to initialize embedding service: {e}") from e
|
|
122
122
|
|
|
123
123
|
|
|
124
|
-
async def get_memory_service(request: Request) -> Optional["
|
|
125
|
-
"""Get the
|
|
124
|
+
async def get_memory_service(request: Request) -> Optional["BaseMemoryService"]:
|
|
125
|
+
"""Get the memory service if configured (defaults to Mem0 implementation)."""
|
|
126
126
|
engine = getattr(request.app.state, "engine", None)
|
|
127
127
|
slug = getattr(request.app.state, "app_slug", None)
|
|
128
128
|
if not engine or not slug:
|
|
@@ -2,9 +2,45 @@
|
|
|
2
2
|
|
|
3
3
|
Mem0.ai integration for intelligent memory management in MDB_ENGINE applications. Provides semantic memory storage, retrieval, and inference capabilities with MongoDB integration.
|
|
4
4
|
|
|
5
|
+
## 🎉 What's New
|
|
6
|
+
|
|
7
|
+
### Extensible Architecture (Latest)
|
|
8
|
+
|
|
9
|
+
**Base Class Pattern for Future Extensibility!**
|
|
10
|
+
|
|
11
|
+
The memory service now uses an abstract base class pattern, enabling future memory provider implementations while maintaining backward compatibility:
|
|
12
|
+
|
|
13
|
+
- **🏗️ BaseMemoryService**: Abstract base class defining the memory service interface
|
|
14
|
+
- **🔌 Provider Extensibility**: Easy to add new memory providers (LangChain, custom implementations, etc.)
|
|
15
|
+
- **✅ Backward Compatible**: All existing code continues to work without changes
|
|
16
|
+
- **📝 Type Safety**: Better IDE support and type checking with abstract base class
|
|
17
|
+
- **🎯 Consistent API**: All memory providers implement the same interface
|
|
18
|
+
|
|
19
|
+
### v0.7.5 Enhancements
|
|
20
|
+
|
|
21
|
+
**Memory Injection and Enhanced Delete Capabilities!**
|
|
22
|
+
|
|
23
|
+
- **💉 Inject Method**: New `inject()` method for manual memory insertion without LLM inference - perfect for adding facts, preferences, or structured data directly
|
|
24
|
+
- **🗑️ Enhanced Delete**: Comprehensive delete functionality with improved documentation and user experience
|
|
25
|
+
- **🧠 Memory Explorer UI**: Added memory explorer interface in chit_chat example with inject and delete buttons
|
|
26
|
+
|
|
27
|
+
### v0.7.4 Enhancements
|
|
28
|
+
|
|
29
|
+
**Enhanced Mem0 Integration - Production Ready!**
|
|
30
|
+
|
|
31
|
+
- **🔧 Hybrid Update Pattern**: Content updates via Mem0 (triggers re-embedding), metadata updates via direct MongoDB (full control, no API limitations)
|
|
32
|
+
- **📊 Direct MongoDB Access**: Reliable data retrieval directly from MongoDB, bypassing Mem0 API inconsistencies
|
|
33
|
+
- **🏷️ Full Metadata Support**: Update any metadata field without restrictions - not limited by Mem0's API
|
|
34
|
+
- **✅ Correct Mem0 Structure**: Properly handles Mem0's MongoDB structure (`_id` as document ID, `payload` for memory data)
|
|
35
|
+
- **🛡️ Robust Error Handling**: Specific exception handling with proper KeyboardInterrupt/SystemExit propagation
|
|
36
|
+
- **🔍 Reliable Returns**: Always returns normalized documents fetched directly from MongoDB (guaranteed structure)
|
|
37
|
+
|
|
38
|
+
> 📖 **Want to understand why we use manual MongoDB access?** See the [Mem0 Implementation Guide](../../docs/guides/MEM0_IMPLEMENTATION.md) for detailed explanations of our architectural decisions, Mem0's MongoDB structure, and things to watch out for.
|
|
39
|
+
|
|
5
40
|
## Features
|
|
6
41
|
|
|
7
|
-
- **
|
|
42
|
+
- **Extensible Architecture**: Base class pattern allows for multiple memory provider implementations
|
|
43
|
+
- **Mem0 Integration**: Default implementation using Mem0.ai for intelligent memory management
|
|
8
44
|
- **MongoDB Storage**: Built-in MongoDB vector store integration
|
|
9
45
|
- **Auto-Detection**: Automatically detects OpenAI or Azure OpenAI from environment variables
|
|
10
46
|
- **Semantic Search**: Vector-based semantic memory search
|
|
@@ -67,7 +103,7 @@ Enable memory service in your `manifest.json`:
|
|
|
67
103
|
### Basic Usage
|
|
68
104
|
|
|
69
105
|
```python
|
|
70
|
-
from mdb_engine.memory import
|
|
106
|
+
from mdb_engine.memory import BaseMemoryService # Base class for type hints
|
|
71
107
|
from mdb_engine.core import MongoDBEngine
|
|
72
108
|
|
|
73
109
|
# Initialize engine
|
|
@@ -75,7 +111,8 @@ engine = MongoDBEngine(mongo_uri="...", db_name="...")
|
|
|
75
111
|
await engine.initialize()
|
|
76
112
|
|
|
77
113
|
# Get memory service (automatically configured from manifest)
|
|
78
|
-
|
|
114
|
+
# Returns BaseMemoryService instance (currently Mem0MemoryService)
|
|
115
|
+
memory_service: BaseMemoryService = engine.get_memory_service("my_app")
|
|
79
116
|
|
|
80
117
|
# Add memory
|
|
81
118
|
memory = await memory_service.add(
|
|
@@ -140,6 +177,45 @@ memories = await memory_service.add_all(
|
|
|
140
177
|
)
|
|
141
178
|
```
|
|
142
179
|
|
|
180
|
+
### Inject Memory (Manual Insertion)
|
|
181
|
+
|
|
182
|
+
Manually inject memories without LLM inference. This is useful when you want to directly add facts, preferences, or structured data without going through the inference pipeline:
|
|
183
|
+
|
|
184
|
+
```python
|
|
185
|
+
# Inject memory as a string
|
|
186
|
+
memory = await memory_service.inject(
|
|
187
|
+
memory="The user prefers dark mode interfaces",
|
|
188
|
+
user_id="user123",
|
|
189
|
+
metadata={"source": "manual", "category": "preference"}
|
|
190
|
+
)
|
|
191
|
+
|
|
192
|
+
# Inject memory as a dict
|
|
193
|
+
memory = await memory_service.inject(
|
|
194
|
+
memory={"memory": "Project deadline is next Friday", "category": "work"},
|
|
195
|
+
user_id="user123",
|
|
196
|
+
metadata={"source": "manual", "type": "deadline"}
|
|
197
|
+
)
|
|
198
|
+
|
|
199
|
+
# Returns: {"id": "...", "memory": "...", "metadata": {...}, ...}
|
|
200
|
+
```
|
|
201
|
+
|
|
202
|
+
**Key Differences from `add()`:**
|
|
203
|
+
- **`inject()`**: Direct insertion without LLM inference (faster, no API costs)
|
|
204
|
+
- **`add()`**: Uses LLM inference to extract facts from messages (slower, costs API calls)
|
|
205
|
+
- **`inject()`**: Returns a single memory dict
|
|
206
|
+
- **`add()`**: Returns a list of extracted memories
|
|
207
|
+
|
|
208
|
+
**When to use `inject()`:**
|
|
209
|
+
- Adding known facts or preferences directly
|
|
210
|
+
- Importing structured data
|
|
211
|
+
- When you want to avoid LLM inference costs
|
|
212
|
+
- When you have pre-formatted memory content
|
|
213
|
+
|
|
214
|
+
**When to use `add()`:**
|
|
215
|
+
- Extracting memories from conversations
|
|
216
|
+
- When you want the LLM to identify key facts
|
|
217
|
+
- Processing unstructured text into memories
|
|
218
|
+
|
|
143
219
|
### Search Memories
|
|
144
220
|
|
|
145
221
|
Semantic search across stored memories:
|
|
@@ -163,14 +239,17 @@ results = await memory_service.search(
|
|
|
163
239
|
|
|
164
240
|
### Get Memories
|
|
165
241
|
|
|
166
|
-
Retrieve memories for a user:
|
|
242
|
+
Retrieve memories for a user. The service automatically normalizes Mem0's MongoDB structure (`_id`, `payload`) into a consistent API format:
|
|
167
243
|
|
|
168
244
|
```python
|
|
169
245
|
# Get all memories
|
|
170
246
|
all_memories = await memory_service.get_all(user_id="user123")
|
|
247
|
+
# Returns normalized format: [{"id": "...", "memory": "...", "metadata": {...}, ...}]
|
|
171
248
|
|
|
172
249
|
# Get specific memory
|
|
173
250
|
memory = await memory_service.get(memory_id="memory_123", user_id="user123")
|
|
251
|
+
# Returns normalized format: {"id": "...", "memory": "...", "metadata": {...}, ...}
|
|
252
|
+
# Note: memory_id can be either Mem0's _id or the normalized id field
|
|
174
253
|
|
|
175
254
|
# Get memories with filters
|
|
176
255
|
memories = await memory_service.get_all(
|
|
@@ -179,9 +258,16 @@ memories = await memory_service.get_all(
|
|
|
179
258
|
)
|
|
180
259
|
```
|
|
181
260
|
|
|
261
|
+
**Note**: The service handles Mem0's internal MongoDB structure (`_id` as document ID, `payload` containing memory data) automatically. All methods return normalized documents with consistent `id`, `memory`, `text`, and `metadata` fields.
|
|
262
|
+
|
|
182
263
|
### Update Memory
|
|
183
264
|
|
|
184
|
-
Update existing memories
|
|
265
|
+
Update existing memories using a **hybrid approach** that combines Mem0's embedding capabilities with direct MongoDB control:
|
|
266
|
+
|
|
267
|
+
**Architecture:**
|
|
268
|
+
- **Content Updates**: Routed via Mem0 (triggers automatic re-embedding)
|
|
269
|
+
- **Metadata Updates**: Routed via direct PyMongo (full control, no API limitations)
|
|
270
|
+
- **Return Value**: Always fetched from MongoDB (guaranteed correct structure)
|
|
185
271
|
|
|
186
272
|
```python
|
|
187
273
|
# Update memory content and metadata
|
|
@@ -200,14 +286,21 @@ updated = memory_service.update(
|
|
|
200
286
|
metadata={"updated": True}
|
|
201
287
|
)
|
|
202
288
|
|
|
203
|
-
# Update only metadata (content unchanged)
|
|
289
|
+
# Update only metadata (content unchanged) - FULLY SUPPORTED
|
|
290
|
+
updated = memory_service.update(
|
|
291
|
+
memory_id="memory_123",
|
|
292
|
+
user_id="user123",
|
|
293
|
+
metadata={"category": "updated", "priority": "high"}
|
|
294
|
+
)
|
|
295
|
+
|
|
296
|
+
# Update only content (no metadata changes)
|
|
204
297
|
updated = memory_service.update(
|
|
205
298
|
memory_id="memory_123",
|
|
206
299
|
user_id="user123",
|
|
207
|
-
|
|
300
|
+
memory="Updated content only"
|
|
208
301
|
)
|
|
209
302
|
|
|
210
|
-
#
|
|
303
|
+
# Using 'data' parameter
|
|
211
304
|
updated = memory_service.update(
|
|
212
305
|
memory_id="memory_123",
|
|
213
306
|
user_id="user123",
|
|
@@ -217,25 +310,63 @@ updated = memory_service.update(
|
|
|
217
310
|
```
|
|
218
311
|
|
|
219
312
|
**Key Features:**
|
|
313
|
+
- **Hybrid Architecture**: Mem0 handles embeddings, MongoDB handles data persistence
|
|
314
|
+
- **Full Metadata Support**: Update any metadata field (not limited by Mem0 API)
|
|
220
315
|
- **Preserves Memory ID**: The original memory ID is maintained
|
|
221
316
|
- **Preserves Creation Timestamp**: `created_at` is not modified
|
|
222
317
|
- **Updates Timestamp**: `updated_at` is automatically set to current time
|
|
223
|
-
- **Recomputes Embeddings**: If content changes, the embedding vector is automatically recomputed
|
|
224
|
-
- **
|
|
318
|
+
- **Recomputes Embeddings**: If content changes, the embedding vector is automatically recomputed via Mem0
|
|
319
|
+
- **Reliable Returns**: Always returns the actual document from MongoDB (not Mem0's response format)
|
|
225
320
|
- **Partial Updates**: Can update content only, metadata only, or both
|
|
321
|
+
- **Security**: Validates user_id ownership before allowing updates
|
|
322
|
+
- **Mem0 Structure Aware**: Correctly handles Mem0's MongoDB structure (`_id` as document ID, `payload` for memory data)
|
|
323
|
+
- **Direct MongoDB Access**: Uses PyMongo for reliable data operations, ensuring consistency
|
|
324
|
+
- **Normalized Responses**: All methods return consistent document structure regardless of Mem0's internal format
|
|
226
325
|
|
|
227
326
|
### Delete Memory
|
|
228
327
|
|
|
229
|
-
Remove memories:
|
|
328
|
+
Remove memories from storage. Both methods return `True` on success, `False` on failure:
|
|
230
329
|
|
|
231
330
|
```python
|
|
232
|
-
# Delete single memory
|
|
233
|
-
await memory_service.delete(memory_id="memory_123", user_id="user123")
|
|
234
|
-
|
|
235
|
-
|
|
236
|
-
|
|
331
|
+
# Delete single memory by ID
|
|
332
|
+
success = await memory_service.delete(memory_id="memory_123", user_id="user123")
|
|
333
|
+
if success:
|
|
334
|
+
print("Memory deleted successfully")
|
|
335
|
+
else:
|
|
336
|
+
print("Failed to delete memory (may not exist)")
|
|
337
|
+
|
|
338
|
+
# Delete all memories for a user (use with caution!)
|
|
339
|
+
success = await memory_service.delete_all(user_id="user123")
|
|
340
|
+
if success:
|
|
341
|
+
print("All memories deleted successfully")
|
|
342
|
+
|
|
343
|
+
# Delete with error handling
|
|
344
|
+
try:
|
|
345
|
+
success = await memory_service.delete(memory_id="memory_123", user_id="user123")
|
|
346
|
+
if not success:
|
|
347
|
+
logger.warning(f"Memory {memory_id} not found or already deleted")
|
|
348
|
+
except Mem0MemoryServiceError as e:
|
|
349
|
+
logger.error(f"Error deleting memory: {e}")
|
|
237
350
|
```
|
|
238
351
|
|
|
352
|
+
**Key Features:**
|
|
353
|
+
- **User Scoping**: Both methods respect `user_id` for security
|
|
354
|
+
- **Safe Deletion**: Returns `False` if memory doesn't exist (doesn't raise exception)
|
|
355
|
+
- **Bulk Deletion**: `delete_all()` removes all memories for a user
|
|
356
|
+
- **Idempotent**: Safe to call multiple times (returns `False` if already deleted)
|
|
357
|
+
|
|
358
|
+
**When to use `delete()`:**
|
|
359
|
+
- Removing a specific memory by ID
|
|
360
|
+
- Cleaning up outdated or incorrect memories
|
|
361
|
+
- User-initiated memory removal
|
|
362
|
+
|
|
363
|
+
**When to use `delete_all()`:**
|
|
364
|
+
- Resetting user memory (e.g., account deletion)
|
|
365
|
+
- Clearing test data
|
|
366
|
+
- Bulk cleanup operations
|
|
367
|
+
|
|
368
|
+
**Note**: Deletion is permanent and cannot be undone. Consider implementing soft deletes if you need to recover deleted memories.
|
|
369
|
+
|
|
239
370
|
### Bucket Organization
|
|
240
371
|
|
|
241
372
|
Organize memories into buckets for better management:
|
|
@@ -336,31 +467,100 @@ for memory in insights:
|
|
|
336
467
|
print(f"Insights: {memory.get('insights')}")
|
|
337
468
|
```
|
|
338
469
|
|
|
470
|
+
## Architecture
|
|
471
|
+
|
|
472
|
+
### Base Class Pattern
|
|
473
|
+
|
|
474
|
+
The memory service uses an abstract base class pattern for extensibility:
|
|
475
|
+
|
|
476
|
+
```python
|
|
477
|
+
from mdb_engine.memory import BaseMemoryService, MemoryServiceError
|
|
478
|
+
|
|
479
|
+
# BaseMemoryService defines the interface
|
|
480
|
+
# Mem0MemoryService implements it (default provider)
|
|
481
|
+
# Future providers can inherit from BaseMemoryService
|
|
482
|
+
```
|
|
483
|
+
|
|
484
|
+
**Benefits:**
|
|
485
|
+
- **Type Safety**: Use `BaseMemoryService` for type hints
|
|
486
|
+
- **Extensibility**: Easy to add new providers (LangChain, custom, etc.)
|
|
487
|
+
- **Consistency**: All providers implement the same interface
|
|
488
|
+
- **Backward Compatible**: Existing code works without changes
|
|
489
|
+
|
|
490
|
+
### Creating Custom Memory Providers
|
|
491
|
+
|
|
492
|
+
To create a custom memory provider, inherit from `BaseMemoryService`:
|
|
493
|
+
|
|
494
|
+
```python
|
|
495
|
+
from mdb_engine.memory import BaseMemoryService, MemoryServiceError
|
|
496
|
+
|
|
497
|
+
class CustomMemoryService(BaseMemoryService):
|
|
498
|
+
"""Custom memory service implementation."""
|
|
499
|
+
|
|
500
|
+
def __init__(self, mongo_uri: str, db_name: str, app_slug: str, config: dict | None = None):
|
|
501
|
+
# Initialize your custom implementation
|
|
502
|
+
pass
|
|
503
|
+
|
|
504
|
+
def add(self, messages, user_id=None, metadata=None, **kwargs):
|
|
505
|
+
# Implement add method
|
|
506
|
+
pass
|
|
507
|
+
|
|
508
|
+
# Implement all other abstract methods...
|
|
509
|
+
def get_all(self, user_id=None, limit=100, filters=None, **kwargs):
|
|
510
|
+
pass
|
|
511
|
+
|
|
512
|
+
def search(self, query, user_id=None, limit=5, filters=None, **kwargs):
|
|
513
|
+
pass
|
|
514
|
+
|
|
515
|
+
def get(self, memory_id, user_id=None, **kwargs):
|
|
516
|
+
pass
|
|
517
|
+
|
|
518
|
+
def delete(self, memory_id, user_id=None, **kwargs):
|
|
519
|
+
pass
|
|
520
|
+
|
|
521
|
+
def delete_all(self, user_id=None, **kwargs):
|
|
522
|
+
pass
|
|
523
|
+
|
|
524
|
+
def update(self, memory_id, user_id=None, memory=None, metadata=None, **kwargs):
|
|
525
|
+
pass
|
|
526
|
+
```
|
|
527
|
+
|
|
339
528
|
## API Reference
|
|
340
529
|
|
|
530
|
+
### BaseMemoryService
|
|
531
|
+
|
|
532
|
+
Abstract base class for all memory service implementations. Defines the standard interface.
|
|
533
|
+
|
|
341
534
|
### Mem0MemoryService
|
|
342
535
|
|
|
536
|
+
Default implementation using Mem0.ai. Inherits from `BaseMemoryService`.
|
|
537
|
+
|
|
343
538
|
#### Initialization
|
|
344
539
|
|
|
345
540
|
```python
|
|
346
541
|
Mem0MemoryService(
|
|
347
542
|
mongo_uri: str,
|
|
348
543
|
db_name: str,
|
|
349
|
-
|
|
350
|
-
|
|
351
|
-
|
|
352
|
-
|
|
353
|
-
|
|
354
|
-
|
|
355
|
-
|
|
356
|
-
|
|
357
|
-
|
|
544
|
+
app_slug: str,
|
|
545
|
+
config: dict = None # Optional configuration
|
|
546
|
+
)
|
|
547
|
+
|
|
548
|
+
# Or use the factory function
|
|
549
|
+
from mdb_engine.memory import get_memory_service
|
|
550
|
+
|
|
551
|
+
memory_service = get_memory_service(
|
|
552
|
+
mongo_uri="...",
|
|
553
|
+
db_name="...",
|
|
554
|
+
app_slug="...",
|
|
555
|
+
config={...},
|
|
556
|
+
provider="mem0" # Default, future providers can be specified here
|
|
358
557
|
)
|
|
359
558
|
```
|
|
360
559
|
|
|
361
560
|
#### Methods
|
|
362
561
|
|
|
363
562
|
- `add(messages, user_id, metadata=None, bucket_id=None, bucket_type=None, store_raw_content=False, raw_content=None)` - Add single memory with optional bucket and raw content storage
|
|
563
|
+
- `inject(memory, user_id, metadata=None)` - Manually inject a memory without LLM inference
|
|
364
564
|
- `add_with_raw_content(messages, raw_content, user_id, bucket_id=None, bucket_type=None)` - Store both extracted facts and raw content
|
|
365
565
|
- `get_buckets(user_id, bucket_type=None, limit=None)` - Get all buckets for a user
|
|
366
566
|
- `get_bucket_memories(bucket_id, user_id, include_raw_content=False, limit=None)` - Get all memories in a bucket
|
|
@@ -513,15 +713,19 @@ knowledge = await memory_service.search(
|
|
|
513
713
|
## Error Handling
|
|
514
714
|
|
|
515
715
|
```python
|
|
516
|
-
from mdb_engine.memory import Mem0MemoryServiceError
|
|
716
|
+
from mdb_engine.memory import MemoryServiceError, Mem0MemoryServiceError
|
|
517
717
|
|
|
518
718
|
try:
|
|
519
719
|
memory = await memory_service.add(
|
|
520
720
|
messages=[{"role": "user", "content": "Test"}],
|
|
521
721
|
user_id="user123"
|
|
522
722
|
)
|
|
523
|
-
except
|
|
723
|
+
except MemoryServiceError as e:
|
|
724
|
+
# Base exception for all memory service errors
|
|
524
725
|
print(f"Memory service error: {e}")
|
|
726
|
+
except Mem0MemoryServiceError as e:
|
|
727
|
+
# Specific exception for Mem0 implementation
|
|
728
|
+
print(f"Mem0 memory service error: {e}")
|
|
525
729
|
except (ValueError, TypeError, ConnectionError) as e:
|
|
526
730
|
print(f"Configuration or connection error: {e}")
|
|
527
731
|
```
|
|
@@ -14,16 +14,25 @@ Key Features:
|
|
|
14
14
|
- **Optional LLM Inference**: Can leverage LLM service for automatic memory
|
|
15
15
|
extraction (set infer: false to disable)
|
|
16
16
|
- **Graph Support**: Optional knowledge graph construction for entity relationships
|
|
17
|
+
- **Extensible Architecture**: Base class allows for future memory provider implementations
|
|
17
18
|
|
|
18
19
|
Dependencies:
|
|
19
20
|
pip install mem0ai
|
|
20
21
|
"""
|
|
21
22
|
|
|
23
|
+
# Import base classes
|
|
24
|
+
from .base import BaseMemoryService, MemoryServiceError
|
|
25
|
+
|
|
22
26
|
# Import service components (mem0 import is lazy within service.py)
|
|
23
27
|
from .service import Mem0MemoryService, Mem0MemoryServiceError, get_memory_service
|
|
24
28
|
|
|
25
29
|
__all__ = [
|
|
30
|
+
# Base classes (for extensibility)
|
|
31
|
+
"BaseMemoryService",
|
|
32
|
+
"MemoryServiceError",
|
|
33
|
+
# Mem0 implementation (default)
|
|
26
34
|
"Mem0MemoryService",
|
|
27
35
|
"Mem0MemoryServiceError",
|
|
36
|
+
# Factory function
|
|
28
37
|
"get_memory_service",
|
|
29
38
|
]
|