fix(mcp): case-insensitive agent name in diary_write/diary_read (#1243)
`tool_diary_write` stored the `agent` metadata verbatim after `sanitize_name` (which preserves case), while `tool_diary_read` filtered by exact match — so writing as "Claude" and reading as "claude" silently returned zero rows. Both endpoints now lowercase `agent_name` immediately after sanitization. The default per-agent wing slug is also stable across casings since it's derived from the same normalized form. Behavior change: entries written prior to this fix under mixed-case agent names will not match the new lowercase filter; documented under v3.3.5 in CHANGELOG with a `mempalace repair` pointer. Adds a regression test (`test_diary_read_case_insensitive_agent`) and updates the existing `test_diary_write_and_read` to assert the new lowercase agent identity. Closes #1243 Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
This commit is contained in:
+13
-4
@@ -677,7 +677,7 @@ def tool_check_duplicate(content: str, threshold: float = 0.9):
|
||||
"vector_disabled": True,
|
||||
"vector_disabled_reason": _vector_disabled_reason,
|
||||
"hint": (
|
||||
"duplicate detection requires vector search; run " "`mempalace repair` to restore"
|
||||
"duplicate detection requires vector search; run `mempalace repair` to restore"
|
||||
),
|
||||
}
|
||||
try:
|
||||
@@ -1133,9 +1133,13 @@ def tool_diary_write(agent_name: str, entry: str, topic: str = "general", wing:
|
||||
|
||||
This is the agent's personal journal — observations, thoughts,
|
||||
what it worked on, what it noticed, what it thinks matters.
|
||||
|
||||
Note: ``agent_name`` is normalized to lowercase before storage so
|
||||
that diary reads are case-insensitive (see #1243). "Claude",
|
||||
"claude", and "CLAUDE" all resolve to the same agent.
|
||||
"""
|
||||
try:
|
||||
agent_name = sanitize_name(agent_name, "agent_name")
|
||||
agent_name = sanitize_name(agent_name, "agent_name").lower()
|
||||
entry = sanitize_content(entry)
|
||||
topic = sanitize_name(topic, "topic")
|
||||
except ValueError as e:
|
||||
@@ -1144,7 +1148,7 @@ def tool_diary_write(agent_name: str, entry: str, topic: str = "general", wing:
|
||||
if wing:
|
||||
wing = sanitize_name(wing)
|
||||
else:
|
||||
wing = f"wing_{agent_name.lower().replace(' ', '_')}"
|
||||
wing = f"wing_{agent_name.replace(' ', '_')}"
|
||||
room = "diary"
|
||||
col = _get_collection(create=True)
|
||||
if not col:
|
||||
@@ -1209,9 +1213,14 @@ def tool_diary_read(agent_name: str, last_n: int = 10, wing: str = ""):
|
||||
written to. Diary writes from hooks land in project-derived wings
|
||||
(``wing_<project>``), so requiring a specific wing on read would
|
||||
silo those entries from agent-initiated reads.
|
||||
|
||||
Note: ``agent_name`` is normalized to lowercase before filtering so
|
||||
that reads are case-insensitive (see #1243). Entries written under
|
||||
pre-fix mixed-case agent names will not match the lowercase filter;
|
||||
use ``mempalace repair`` to migrate legacy data if needed.
|
||||
"""
|
||||
try:
|
||||
agent_name = sanitize_name(agent_name, "agent_name")
|
||||
agent_name = sanitize_name(agent_name, "agent_name").lower()
|
||||
if wing:
|
||||
wing = sanitize_name(wing)
|
||||
except ValueError as e:
|
||||
|
||||
Reference in New Issue
Block a user