Skip to content

MongoDB Implementation Bug: update replaces metadata entirely #3966

@ranfysvalle02

Description

@ranfysvalle02

🐛 Describe the bug

#3966

Mem0 Update Payload Replacement Issue

Problem

Mem0's MongoDB vector store update() method replaces the entire payload field when updating a memory, causing complete loss of metadata if not handled correctly.

Root Cause

Mem0's vector store implementation does:

def update(self, vector_id: str, vector: Optional[List[float]] = None, payload: Optional[Dict] = None) -> None:
    update_fields = {}
    if vector is not None:
        update_fields["embedding"] = vector
    if payload is not None:
        update_fields["payload"] = payload  # ⚠️ REPLACES ENTIRE PAYLOAD

    if update_fields:
        self.collection.update_one({"_id": vector_id}, {"$set": update_fields})

When Mem0's memory.update() is called, it internally calls the vector store's update() method with a new payload, which results in:

// MongoDB operation
{"$set": {"payload": new_payload}}  // ⚠️ This REPLACES the entire payload object

Result: All existing metadata fields (bucket_id, context_id, category, source, etc.) are completely lost unless explicitly preserved.

Impact

  • Metadata Loss: All custom metadata fields are wiped when updating memory content
  • Data Integrity: Critical fields like bucket_id, context_id, category disappear
  • User Experience: UI shows "Ungrouped" memories, filters break, context is lost

Update memory content (without metadata preservation)

Without our fix, if you call Mem0 directly:

# ⚠️ THIS LOSES METADATA
from mem0 import Memory

mem0 = Memory.from_config({...})
mem0.update(memory_id=memory_id, data="User loves chocolate and vanilla")

# Check metadata - ALL GONE!
updated = memory_service.get(memory_id=memory_id, user_id="user123")
print(f"Metadata after update: {updated['metadata']}")
# Output: {}  # ⚠️ EMPTY! All metadata lost!

3. Verify metadata loss

# Fetch the memory
memory = memory_service.get(memory_id=memory_id, user_id="user123")

# Check metadata
assert "bucket_id" not in memory.get("metadata", {}), "Metadata should be lost!"
assert "source" not in memory.get("metadata", {}), "Metadata should be lost!"
# These assertions will PASS (metadata is gone)

Potential Future Fixes

Option 1: Patch Mem0's Vector Store (Upstream Fix)

Ideal Solution: Modify Mem0's MongoDB vector store to merge payload instead of replacing:

# In mem0/vector_stores/mongodb.py
def update(self, vector_id: str, vector: Optional[List[float]] = None, payload: Optional[Dict] = None) -> None:
    update_fields = {}
    if vector is not None:
        update_fields["embedding"] = vector
    if payload is not None:
        # ✅ MERGE instead of REPLACE
        for k, v in payload.items():
            update_fields[f"payload.{k}"] = v
        # Instead of: update_fields["payload"] = payload
    
    if update_fields:
        self.collection.update_one({"_id": vector_id}, {"$set": update_fields})

Pros:

  • Fixes the issue at the source
  • Benefits all Mem0 users
  • Cleaner architecture

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions