Refactor client API based on OpenAPI spec and add mem0_delete tool

- Update client.py to use correct API endpoints from OpenAPI spec
- Add delete() method for memory deletion
- Add mem0_delete tool with schema and handler
- Simplify API calls to match actual Mem0 OSS server format
This commit is contained in:
2026-04-10 13:24:14 +02:00
parent fdd2a07ae5
commit 6e7c6dd3ce
3 changed files with 102 additions and 79 deletions
+47 -27
View File
@@ -112,6 +112,24 @@ CONCLUDE_SCHEMA = {
},
}
DELETE_SCHEMA = {
"name": "mem0_delete",
"description": (
"Delete a specific memory by ID. Use when user explicitly requests "
"to remove or forget a stored fact."
),
"parameters": {
"type": "object",
"properties": {
"memory_id": {
"type": "string",
"description": "The ID of the memory to delete.",
},
},
"required": ["memory_id"],
},
}
# ---------------------------------------------------------------------------
# MemoryProvider implementation
@@ -279,9 +297,8 @@ class Mem0LocalMemoryProvider(MemoryProvider):
client = self._get_client()
results = client.search(
query=query,
filters=self._read_filters(),
rerank=self._rerank,
top_k=5,
user_id=self._user_id,
limit=5,
)
if results:
lines = [
@@ -311,11 +328,12 @@ class Mem0LocalMemoryProvider(MemoryProvider):
def _sync():
try:
client = self._get_client()
messages = [
{"role": "user", "content": user_content},
{"role": "assistant", "content": assistant_content},
]
client.add(messages, filters=self._write_filters(), infer=True)
# Combine user and assistant content for context
combined = f"User: {user_content}\nAssistant: {assistant_content}"
client.add(
message=combined,
user_id=self._user_id,
)
self._record_success()
except Exception as e:
self._record_failure()
@@ -330,7 +348,7 @@ class Mem0LocalMemoryProvider(MemoryProvider):
self._sync_thread.start()
def get_tool_schemas(self) -> List[Dict[str, Any]]:
return [PROFILE_SCHEMA, SEARCH_SCHEMA, CONCLUDE_SCHEMA]
return [PROFILE_SCHEMA, SEARCH_SCHEMA, CONCLUDE_SCHEMA, DELETE_SCHEMA]
def handle_tool_call(self, tool_name: str, args: dict, **kwargs) -> str:
if self._is_breaker_open():
@@ -347,15 +365,11 @@ class Mem0LocalMemoryProvider(MemoryProvider):
if tool_name == "mem0_profile":
try:
memories = client.get_all(filters=self._read_filters())
memories = client.get_all(user_id=self._user_id)
self._record_success()
if not memories:
return json.dumps({"result": "No memories stored yet."})
lines = [
m.get("text") or m.get("memory", "")
for m in memories
if m.get("text") or m.get("memory")
]
lines = [m.get("text", "") for m in memories if m.get("text")]
return json.dumps({"result": "\n".join(lines), "count": len(lines)})
except Exception as e:
self._record_failure()
@@ -365,23 +379,18 @@ class Mem0LocalMemoryProvider(MemoryProvider):
query = args.get("query", "")
if not query:
return tool_error("Missing required parameter: query")
rerank = args.get("rerank", False)
top_k = min(int(args.get("top_k", 10)), 50)
try:
results = client.search(
query=query,
filters=self._read_filters(),
rerank=rerank,
top_k=top_k,
user_id=self._user_id,
limit=top_k,
)
self._record_success()
if not results:
return json.dumps({"result": "No relevant memories found."})
items = [
{
"memory": r.get("text") or r.get("memory", ""),
"score": r.get("score", 0),
}
{"memory": r.get("text", ""), "score": r.get("score", 0)}
for r in results
]
return json.dumps({"results": items, "count": len(items)})
@@ -395,9 +404,8 @@ class Mem0LocalMemoryProvider(MemoryProvider):
return tool_error("Missing required parameter: conclusion")
try:
client.add(
[{"role": "user", "content": conclusion}],
filters=self._write_filters(),
infer=False, # Store verbatim
message=conclusion,
user_id=self._user_id,
)
self._record_success()
return json.dumps({"result": "Fact stored."})
@@ -405,6 +413,18 @@ class Mem0LocalMemoryProvider(MemoryProvider):
self._record_failure()
return tool_error(f"Failed to store: {e}")
elif tool_name == "mem0_delete":
memory_id = args.get("memory_id", "")
if not memory_id:
return tool_error("Missing required parameter: memory_id")
try:
client.delete(memory_id=memory_id)
self._record_success()
return json.dumps({"result": "Memory deleted."})
except Exception as e:
self._record_failure()
return tool_error(f"Failed to delete: {e}")
return tool_error(f"Unknown tool: {tool_name}")
def shutdown(self) -> None:
@@ -435,7 +455,7 @@ def register(ctx) -> None:
"""Create a handler closure for a specific tool."""
return lambda args, **kwargs: provider.handle_tool_call(tool_name, args)
for schema in [PROFILE_SCHEMA, SEARCH_SCHEMA, CONCLUDE_SCHEMA]:
for schema in [PROFILE_SCHEMA, SEARCH_SCHEMA, CONCLUDE_SCHEMA, DELETE_SCHEMA]:
ctx.register_tool(
name=schema["name"],
toolset="mem0_local",