Skip to main content

Agno's clear_memory tool wipes every user's memories: how to scope Agno agent memory per user

Agno issue #9983: the clear_memory tool that MemoryManager can give the model calls db.clear_memories() with no user filter. How to check if you're exposed, the flags to use, a scoped per-user wipe and a guard, checked on agno 3.1.10.

Updated 7 min readMarkdown

Disclosure: I'm Mohammed, founder of MemorySync. I drafted this article with AI assistance and reviewed it for accuracy against the official Agno and MemorySync docs. Code status: on Oct 26, 2026 I ran the same calls as Steps 1, 3 and 4 (the reproduction, the per-user delete and the guard) in scratch scripts on agno 3.1.10 (Python 3.13, a local SQLite file), with no model and no API keys. In Step 5 I only constructed the agent and called clear_memories() with a placeholder key, which raised before any request. No LLM was called and no MemorySync request was made, so memory extraction and recall were not run. The rest is adapted from the docs.

If you run one Agno agent for many users, you probably keep every user's memories in one database and separate them with user_id. agno-agi/agno#9983 shows where that breaks: the clear_memory tool that MemoryManager can hand to the model calls db.clear_memories() with no user filter. One user's session can delete every user's memories.

Below: how to check whether your setup can reach that tool, the settings that keep it away from the model, a per-user wipe that stays scoped, and a small guard you can add today. Agno behaviour comes from the Agno memory docs, the MemoryManager reference and the installed package. I'm building MemorySync, a hosted memory layer, and it gets one short section near the end (if you want it with Agno, see the MemorySync Agno guide).

What the issue found

MemoryManager builds a set of memory tools for model-driven memory work: add_memory, update_memory, delete_memory and clear_memory. The first three pass the current user_id. clear_memory doesn't:

def clear_memory() -> str:
    db.clear_memories()
    ...

The reporter says clear_memories() deletes the whole memories table in every database driver (SQLite, PostgreSQL, MySQL and MongoDB). A fix that routes the tool through the scoped clear_user_memories(user_id=...) is up as PR #9986. On Oct 26, 2026 the issue and the PR were both still open, and agno 3.1.10, the latest release on PyPI that day, still has the unscoped tool.

Step 1: Reproduce it in a few lines (no model needed)

This follows the issue's reproduction. _get_db_tools is a private method; it's used here only to call the tool exactly as the agent would:

from agno.db.sqlite import SqliteDb
from agno.memory import MemoryManager, UserMemory

db = SqliteDb(db_file="memories.db")
db.upsert_user_memory(UserMemory(user_id="user-alice", memory="Alice books window seats."))
db.upsert_user_memory(UserMemory(user_id="user-bob", memory="Bob prefers aisle seats."))

manager = MemoryManager(db=db)
tools = {f.__name__: f for f in manager._get_db_tools(
    "user-alice", db, "fixture",
    enable_add_memory=True, enable_update_memory=True,
    enable_delete_memory=True, enable_clear_memory=True,
)}
tools["clear_memory"]()  # a tool call inside Alice's session

print([m.memory for m in db.get_user_memories(user_id="user-bob")])

On agno 3.1.10 this printed Memory cleared successfully and then []. Bob's memory was gone after a call made in Alice's session.

Step 2: Check whether the model can reach clear_memory

In agno 3.1.10, the model only gets this tool in one situation:

  • Automatic memory (update_memory_on_run=True): the background memory call is built with enable_clear_memory=False, so clear_memory is never offered. Agno's production best practices recommend automatic memory by default anyway.
  • Agentic memory (enable_agentic_memory=True): the agent gets an update_user_memory tool, and the nested memory call offers the tools your MemoryManager flags allow. clear_memory is included only if you set MemoryManager(clear_memories=True).

The MemoryManager reference lists clear_memories as "Allow the manager to clear all memories", default False. So the setting to look for is clear_memories=True. If you need users to be able to say "forget everything about me", use delete_memories=True instead. The agentic memory docs say it lets the tool delete memories for the current user_id:

from agno.agent import Agent
from agno.memory import MemoryManager

agent = Agent(
    model=...,  # your model
    db=db,
    memory_manager=MemoryManager(delete_memories=True),  # leave clear_memories at False
    enable_agentic_memory=True,
)

With these flags, I checked the tool list the memory call would get: add_memory, delete_memory, update_memory, and no clear_memory.

Also look through your own code for MemoryManager.clear() and db.clear_memories(). The reference says clear() "has no user scope and clears the entire memory store".

Step 3: Wipe one user's memories in your own code

For an admin action or a "delete my data" endpoint, call the scoped method with the authenticated user's ID:

manager.clear_user_memories(user_id="user-alice")
# async database: await manager.aclear_user_memories(user_id="user-alice")

In my run, Alice had no memories left afterwards and Bob still had his. Always pass user_id explicitly. Per the reference, user-scoped methods fall back to a user called "default" when it's omitted, and the best practices page says not to rely on it.

Step 4: Add a guard until the fix ships

If you want the global wipe gone no matter which flags someone sets later, subclass your database and make clear_memories() refuse. This is my addition, not something from the Agno docs:

from agno.db.sqlite import SqliteDb

class NoGlobalClearSqliteDb(SqliteDb):
    def clear_memories(self) -> None:
        raise RuntimeError(
            "Global memory wipe is disabled. Use clear_user_memories(user_id=...)."
        )

db = NoGlobalClearSqliteDb(db_file="memories.db")

With this in place, running Step 1 again made the clear_memory tool raise instead of deleting, and Bob's memory stayed. clear_user_memories(user_id=...) still worked, because it deletes one user's memories by ID and never calls clear_memories(). The same override works for the PostgreSQL, MySQL or MongoDB classes. I only ran it on SQLite.

Step 5 (optional): Keep memories in MemorySync

MemorySync's Agno guide plugs a MemorySyncDb into Agno's own MemoryManager. Sessions stay in your database, and memories go to MemorySync. Its clear_memories() always raises, and the per-user wipe is an explicit forget_user_memories(user_id):

pip install agno-memorysync
from agno.agent import Agent
from agno.db.sqlite import SqliteDb
from agno.memory import MemoryManager
from agno_memorysync import MemorySyncDb

memory_db = MemorySyncDb()  # reads MEMORYSYNC_API_KEY

agent = Agent(
    db=SqliteDb(db_file="agent.db"),                # sessions: local
    memory_manager=MemoryManager(db=memory_db),     # memories: MemorySync
    update_memory_on_run=True,
    user_id="customer-42",
)

memory_db.forget_user_memories("customer-42")      # one user's memories, returns the count

The guide requires Python 3.10+ and agno 2.8 or newer, and you create the API key in the dashboard under Settings → API Keys. MemorySyncDb only handles memory. If you point sessions or knowledge at it, it raises MemorySyncMemoryOnlyError, so keep those on your own database. In my run, constructing the agent worked, and clear_memories() raised MemorySyncClearAllError before sending anything. You don't need MemorySync for Steps 1 to 4.

Troubleshooting

  • All users' memories disappeared after a chat. Check for MemoryManager(clear_memories=True) with agentic memory, and for clear() or clear_memories() calls in your code. Then add the Step 4 guard.
  • Memories from different users get mixed. Pass the authenticated user_id on every run and every MemoryManager call. An omitted ID means "default".
  • clear_user_memories() raises with an async database. Use aclear_user_memories(). The reference says the sync version requires a synchronous database.
  • MemorySyncMemoryOnlyError. You pointed a session or knowledge surface at MemorySyncDb. Only memory_manager= should use it.

Common questions

Does Agno's clear_memory tool delete only the current user's memories? Not in agno 3.1.10. The tool calls db.clear_memories(), which isn't filtered by user (agno#9983). A fix that scopes it to the calling user is proposed in PR #9986, which was still open on Oct 26, 2026.

How do I delete all memories for one user in Agno? Call MemoryManager.clear_user_memories(user_id=...), or aclear_user_memories(...) with an async database. The reference describes both as clearing only the selected user's memories (MemoryManager reference).

Is Agno memory isolated per user by default? Memories are stored and read by user_id. The multi-user chat example scopes history by session_id and memory by user_id. If you omit the ID, Agno uses "default", and clear() / clear_memories() ignore user scope entirely.

Can I use MemorySync as Agno's memory backend? Yes. MemorySyncDb from agno-memorysync goes into MemoryManager(db=...), while sessions stay in your own database. Its clear_memories() always raises, and per-user wipes use forget_user_memories(user_id) (MemorySync Agno guide).

Sources

  • GitHub issue agno-agi/agno#9983 and PR #9986 (both open on 2026-10-26)
  • Agno docs: docs.agno.com/memory/overview, /reference/memory/memory, /memory/agent/agentic-memory, /memory/agent/multi-user-multi-session-chat, /memory/best-practices
  • agno 3.1.10 source (agno/memory/manager.py: _get_db_tools, create_user_memories, update_memory_task) and PyPI (agno 3.1.10, agno-memorysync 1.1.0)
  • MemorySync Agno guide: docs.memorysync.io/guides/agno

Try it

If you want to see a memory survive a full page reload before wiring up an agent, the MemorySync playground runs the save, reload and recall loop in your browser: memorysync.io/try.

About the author

  • Building MemorySync (memorysync.io) — persistent memory infrastructure for AI agents, Cursor, and Claude Code.

No comments yet. Be the first to comment.